<!doctype html>
<html lang="en"><head>
  <title>Service Workers</title>
  <meta http-equiv="Content-Type" content="text/html;charset=utf-8"><style>em.rfc2119 {
    text-transform:     lowercase;
    font-variant:       small-caps;
    font-style:         normal;
    color:              #900;
}

body {
/*  padding: 2em 1em 2em 70px;
  margin: 0; */
  color: black;
  background: white;
  background-position: top left;
  background-attachment: fixed;
  background-repeat: no-repeat;

/*  line-height: 1.5em;*/
}

.logo > a {
  border-bottom: none;
}

article, aside, footer, header, hgroup, main, nav, section {
  display: block;
}

header {
  font-weight: bold;
  margin-top: 20px;
  margin-bottom: 20px;
}

header::after {
clear: both;
display: block;
content: " ";
height: 0;
}

section > header > h1, section > header > h2, section > header > h3, section > header > h4, section > header > h5 {
  display: inline;
  font-size: 100%;
  font-weight: bold;
}

body > pre.prettyprint,
body > section pre {
  background-color: #eee;
  padding: 0 2em 1em 2em;
  margin: 0;
  border: none;
}

header > ul {
  font-size: 0.8em;
  list-style: none;
  margin: 0 -1em;
  padding: 0.3em 0;
  background-color: #eee;
}

header > ul > li {
  display: inline;
  margin: 0 0 0 1em;
}

header > ul > li:nth-of-type(3) {
  display: inline;
  margin: 0 0 0 5em;
}

var {
  color: #005A9C;
  font-style: normal;
}

.section-number, .anchor > a {
color: #005A9C;
}

.anchor {
padding-right: 1em;
font-size: 0.8em;
float: right;
text-decoration: none;
}

.fixme {
  display: block;
  padding: 10px 0 0 20px;
  border-left: 5px solid #E05252;
}


.fixme:before {
  content: 'To be addressed';
  float: right;
  display: block;
  padding: 2px 10px;
  background-image: -webkit-linear-gradient(top left, #FFFFFF 0%, #FBE9E9 100%);
  background-image: linear-gradient(to bottom right, #FFFFFF 0%, #FBE9E9 100%);
  font-size: 0.9em;
}

.note {
  color: green;
  font-weight: bold;
  font-style: italic;
  padding-left: 2em;
}

.note:before {
  content: "Note: ";
}

.warning:before {
  content: "WARNING: ";
  font-weight: bold;
}

.warning {
  padding: 10px 10px;
  width: 100%;
  background: #fffaba;
  box-sizing: border-box;
}

dfn {
  font-style: normal;
  font-weight: bold;
  background-color: #f9f9f9;
  padding: 0 2px;
  outline: 1px solid #eee;
}

dfn > code {
  background-color: transparent;
}

dfn.no-references {
  background-color: #ffefef;
}

dfn:target, a:target {
  background-color: #FFFF91;
}

a[href*=dfn-] {
  border-bottom: 1px dotted #ccc;
}

div.informative:before {
  content: 'Informative';
  float: right;
  display: block;
  padding: 2px 10px;
  background-image: -webkit-linear-gradient(top left, #FFFFFF 0%, #D3EEDF 100%);
  background-image: linear-gradient(to bottom right, #FFFFFF 0%, #D3EEDF 100%);
  font-size: 0.9em;
}

div.informative {
  padding: 10px 0 0 20px;
  border-left: 5px solid #D3EEDF;
}

div.monkeypatch:before {
  content: 'Monkeypatch';
  float: right;
  display: block;
  padding: 2px 10px;
  background-image: -webkit-linear-gradient(top left, #FFFFFF 0%, #D3EEDF 100%);
  background-image: linear-gradient(to bottom right, #FFFFFF 0%, #D3EEDF 100%);
  font-size: 0.9em;
}

div.monkeypatch {
  padding: 10px 0 0 20px;
  border-left: 5px solid #EEE5D3;
}

div.deprecated:before {
  content: 'Deprecated parts';
  float: right;
  display: block;
  padding: 2px 10px;
  background-image: -webkit-linear-gradient(top left, #FFFFFF 0%, #fffaba 100%);
  background-image: linear-gradient(to bottom right, #FFFFFF 0%, #fffaba 100%);
  font-size: 0.9em;
}

div.deprecated {
  opacity: 0.6;
}

table {
  border: 1px solid #ccc;
}
table code {
  background-color: transparent;
}
td, th {
  padding: 0.5em;
  vertical-align: top;
}
td {
  border-bottom: 1px solid #ddd;
}
tr:last-of-type td {
  border-bottom: none;
}
th {
  text-align: left;
  background-color: #eee;
}
/*
dt, dd {
  margin-top: 0;
  margin-bottom: 0;
}
dt {
  font-weight: bold;
}
dd {
  padding-bottom: 7px;
}
*/
div.algorithm {
  padding: 0 0 0 20px;
  border-left: 5px solid #EAF7F9;
}
pre {
  background-color: #eee;
  padding: 0.5em 1em 0.5em 1em;
  margin: 0;
  border: none;
}
code {
  background-color: #eee;
  font-family: 'Droid Sans Mono', monospace;
  font-size: 0.9em;
}
code > ins {
  background-color: #BBFFDF;
  text-decoration: none;
}
code > del {
  background-color: #FF979D;
}
nav > ol {
  font-size: 0.9em;
}
nav ol {
  font-weight: normal;
  padding-left:0;
  margin-left: 0;
}

/* Browsers don't support ::marker or display:marker, so emulate it. */
nav li {
  list-style-type: none;
}
nav.marker { display: inline-block; }
nav li .marker { width: 1em; text-align: left; }
nav ol ol { margin-left: 1.75em; }
nav li li .marker { width: 2em; }
nav ol ol ol { margin-left: 2em; }
nav li li li .marker { width: 3em; }
nav ol ol ol ol { margin-left: 3em; }
nav li li li li .marker { width: 3.25em; }
</style>

  <link rel="stylesheet" href="https://www.w3.org/StyleSheets/TR/W3C-WD" type="text/css">


  <meta name="bug.short_desc" content="[ServiceWorker]: ">
  <meta name="bug.product" content="WebAppsWG">
  <meta name="bug.component" content="ServiceWorker">
</head>
<body>

<div class="head">
  <div class="logo">
    <a href="//www.w3.org/"><img width="72" height="48" src="//www.w3.org/Icons/w3c_home" alt="W3C"></a>
  </div>



  <h1>Service Workers</h1>
  <h2 id="w3c-working-draft-25-June-2015">W3C Working Draft 25 June 2015</h2>
  <dl>
  <dt>This version</dt>
    <dd><a href="http://www.w3.org/TR/2015/WD-service-workers-20150625/">http://www.w3.org/TR/2015/WD-service-workers-20150625/</a></dd>
  <dt>Latest published version</dt>
    <dd><a href="http://www.w3.org/TR/service-workers/">http://www.w3.org/TR/service-workers/</a></dd>
  <dt>Latest editor's draft</dt>
    <dd><a href="https://slightlyoff.github.io/ServiceWorker/spec/service_worker/">https://slightlyoff.github.io/ServiceWorker/spec/service_worker/</a></dd>
  <dt>Previous version</dt>
    <dd><a href="http://www.w3.org/TR/2015/WD-service-workers-20150205/">http://www.w3.org/TR/2015/WD-service-workers-20150205/</a></dd>
  <dt>Revision history</dt>
    <dd><a id="log" href="https://github.com/slightlyoff/ServiceWorker/commits/master">https://github.com/slightlyoff/ServiceWorker/commits/master</a></dd>
  <dt>Participate</dt>
    <dd>Discuss on <a href="http://lists.w3.org/Archives/Public/public-webapps/">public-webapps@w3.org</a> (<a href="http://www.w3.org/2008/webapps/">Web Applications Working Group</a>)</dd>
    <dd><a href="https://github.com/slightlyoff/ServiceWorker/issues">File bugs</a></dd>
  <dt>Editors</dt>
    <dd class="vcard"><span class="fn">Alex Russell</span>, <span class="org">Google</span>, &lt;<a class="email" href="mailto:slightlyoff@chromium.org">slightlyoff@chromium.org</a>&gt;</dd>
    <dd class="vcard"><span class="fn">Jungkee Song</span>, <span class="org">Samsung Electronics</span>, &lt;<a class="email" href="mailto:slightlyoff@chromium.org">jungkee.song@samsung.com</a>&gt;</dd>
    <dd class="vcard"><span class="fn">Jake Archibald</span>, <span class="org">Google</span>, &lt;<a class="email" href="mailto:jakearchibald@chromium.org">jakearchibald@chromium.org</a>&gt;</dd>
  </dl>

  <p class="copyright"><a href="http://www.w3.org/Consortium/Legal/ipr-notice#Copyright">Copyright</a> © 2015 <a href="http://www.w3.org/"><abbr title="World Wide Web Consortium">W3C</abbr></a><sup>®</sup> (<a href="http://www.csail.mit.edu/"><abbr title="Massachusetts Institute of Technology">MIT</abbr></a>, <a href="http://www.ercim.eu/"><abbr title="European Research Consortium for Informatics and Mathematics">ERCIM</abbr></a>, <a href="http://www.keio.ac.jp/">Keio</a>, <a href="http://ev.buaa.edu.cn/">Beihang</a>). W3C <a href="http://www.w3.org/Consortium/Legal/ipr-notice#Legal_Disclaimer">liability</a>, <a href="http://www.w3.org/Consortium/Legal/ipr-notice#W3C_Trademarks">trademark</a> and <a href="http://www.w3.org/Consortium/Legal/copyright-documents">document use</a> rules apply.</p>

  <hr>
</div>

  <h2 id="abstract">Abstract</h2>

  <p>This specification describes a method that enables applications to take advantage of persistent background processing, including hooks to enable bootstrapping of web applications while offline.</p>

  <p>The core of this system is an event-driven <a href="http://www.w3.org/TR/workers/">Web Worker</a>, which responds to events dispatched from documents and other sources. A system for managing installation, versions, and upgrades is provided.</p>

  <p>The service worker is a generic entry point for event-driven background processing in the Web Platform that is <a href="#extensibility">extensible by other specifications</a>.</p>

  <h2 id="status">Status of This Document</h2>

<p><em>This section describes the status of this document at the time of its publication. Other documents may supersede this document. A list of current <abbr title="World Wide Web Consortium">W3C</abbr> publications and the latest revision of this technical report can be found in the <a href="http://www.w3.org/TR/"><abbr title="World Wide Web Consortium">W3C</abbr> technical reports index</a> at http://www.w3.org/TR/.</em></p>

<p>This document was published by the <a href="http://www.w3.org/2008/webapps/">Web Applications Working Group</a> as a Working Draft. If you wish to make comments regarding this document, please send them to <a href="mailto:public-webapps@w3.org">public-webapps@w3.org</a> (<a href="mailto:public-webapps-request@w3.org?subject=subscribe">subscribe</a>, <a href="http://lists.w3.org/Archives/Public/public-webapps/">archives</a>). All feedback is welcome.</p><p>Publication as a Working Draft does not imply endorsement by the <abbr title="World Wide Web Consortium">W3C</abbr> Membership. This is a draft document and may be updated, replaced or obsoleted by other documents at any time. It is inappropriate to cite this document as other than work in progress.</p>

<p>This document was produced by a group operating under the <a href="http://www.w3.org/Consortium/Patent-Policy-20040205/">5 February 2004 <abbr title="World Wide Web Consortium">W3C</abbr> Patent Policy</a>. <abbr title="World Wide Web Consortium">W3C</abbr> maintains a <a href="http://www.w3.org/2004/01/pp-impl/42538/status" rel="disclosure">public list of any patent disclosures</a> made in connection with the deliverables of the group; that page also includes instructions for disclosing a patent. An individual who has actual knowledge of a patent which the individual believes contains <a href="http://www.w3.org/Consortium/Patent-Policy-20040205/#def-essential">Essential Claim(s)</a> must disclose the information in accordance with <a href="http://www.w3.org/Consortium/Patent-Policy-20040205/#sec-Disclosure">section 6 of the <abbr title="World Wide Web Consortium">W3C</abbr> Patent Policy</a>.</p>

<p>This document is governed by the <a id="w3c_process_revision" href="http://www.w3.org/2014/Process-20140801/">1 August 2014 <abbr title="World Wide Web Consortium">W3C</abbr> Process Document</a>.</p>

<nav><h2 id="toc">Table of Contents</h2><ol><li><span class="marker">1 </span><a href="#introduction">Introduction</a><ol><li><span class="marker">1.1 </span><a href="#about">About this Document</a></li><li><span class="marker">1.2 </span><a href="#dependencies">Dependencies</a></li><li><span class="marker">1.3 </span><a href="#motivations">Motivations</a></li></ol></li><li><span class="marker">2 </span><a href="#model">Model</a><ol><li><span class="marker">2.1 </span><a href="#service-worker-concept">Service Worker</a><ol><li><span class="marker">2.1.1 </span><a href="#service-worker-lifetime">Lifetime</a></li></ol></li><li><span class="marker">2.2 </span><a href="#service-worker-registration-concept">Service Worker Registration</a><ol><li><span class="marker">2.2.1 </span><a href="#service-worker-registration-lifetime">Lifetime</a></li></ol></li><li><span class="marker">2.3 </span><a href="#service-worker-client-concept">Service Worker Client</a></li></ol></li><li><span class="marker">3 </span><a href="#document-context">Client Context</a><ol><li><span class="marker">3.1 </span><a href="#service-worker-obj">ServiceWorker</a><ol><li><span class="marker">3.1.1 </span><a href="#service-worker-url">scriptURL</a></li><li><span class="marker">3.1.2 </span><a href="#service-worker-state">state</a></li><li><span class="marker">3.1.3 </span><a href="#service-worker-id">id</a></li><li><span class="marker">3.1.4 </span><a href="#service-worker-postmessage">postMessage(<var>message</var>, <var>transfer</var>)</a></li><li><span class="marker">3.1.5 </span><a href="#service-worker-event-handler">Event handler</a></li></ol></li><li><span class="marker">3.2 </span><a href="#service-worker-registration-obj">ServiceWorkerRegistration</a><ol><li><span class="marker">3.2.1 </span><a href="#navigator-service-worker-installing">installing</a></li><li><span class="marker">3.2.2 </span><a href="#navigator-service-worker-waiting">waiting</a></li><li><span class="marker">3.2.3 </span><a href="#navigator-service-worker-active">active</a></li><li><span class="marker">3.2.4 </span><a href="#service-worker-registration-scope">scope</a></li><li><span class="marker">3.2.5 </span><a href="#service-worker-registration-update">update()</a></li><li><span class="marker">3.2.6 </span><a href="#navigator-service-worker-unregister">unregister()</a></li><li><span class="marker">3.2.7 </span><a href="#service-worker-registration-event-handler">Event handler</a></li></ol></li><li><span class="marker">3.3 </span><a href="#navigator-service-worker">navigator.serviceWorker</a></li><li><span class="marker">3.4 </span><a href="#service-worker-container">ServiceWorkerContainer</a><ol><li><span class="marker">3.4.1 </span><a href="#navigator-service-worker-controller">controller</a></li><li><span class="marker">3.4.2 </span><a href="#navigator-service-worker-ready">ready</a></li><li><span class="marker">3.4.3 </span><a href="#navigator-service-worker-register">register(<var>scriptURL</var>, <var>options</var>)</a></li><li><span class="marker">3.4.4 </span><a href="#navigator-service-worker-getRegistration">getRegistration(<var>clientURL</var>)</a></li><li><span class="marker">3.4.5 </span><a href="#navigator-service-worker-getRegistrations">getRegistrations()</a></li><li><span class="marker">3.4.6 </span><a href="#service-worker-container-event-handlers">Event handlers</a></li></ol></li><li><span class="marker">3.5 </span><a href="#serviceworkermessage-event-section">ServiceWorkerMessageEvent</a><ol><li><span class="marker">3.5.1 </span><a href="#serviceworkermessage-event-data">event.data</a></li><li><span class="marker">3.5.2 </span><a href="#serviceworkermessage-event-origin">event.origin</a></li><li><span class="marker">3.5.3 </span><a href="#serviceworkermessage-event-lasteventid">event.lastEventId</a></li><li><span class="marker">3.5.4 </span><a href="#serviceworkermessage-event-source">event.source</a></li><li><span class="marker">3.5.5 </span><a href="#serviceworkermessage-event-ports">event.ports</a></li></ol></li><li><span class="marker">3.6 </span><a href="#document-context-events">Events</a></li></ol></li><li><span class="marker">4 </span><a href="#execution-context">Execution Context</a><ol><li><span class="marker">4.1 </span><a href="#service-worker-global-scope">ServiceWorkerGlobalScope</a><ol><li><span class="marker">4.1.1 </span><a href="#service-worker-global-scope-clients">clients</a></li><li><span class="marker">4.1.2 </span><a href="#service-worker-global-scope-registration">registration</a></li><li><span class="marker">4.1.3 </span><a href="#service-worker-global-scope-skipwaiting">skipWaiting()</a></li><li><span class="marker">4.1.4 </span><a href="#service-worker-global-scope-event-handlers">Event handlers</a></li></ol></li><li><span class="marker">4.2 </span><a href="#client">Client</a><ol><li><span class="marker">4.2.1 </span><a href="#client-url">url</a></li><li><span class="marker">4.2.2 </span><a href="#client-frametype">frameType</a></li><li><span class="marker">4.2.3 </span><a href="#client-id">id</a></li><li><span class="marker">4.2.4 </span><a href="#client-postmessage">postMessage(<var>message</var>, <var>transfer</var>)</a></li><li><span class="marker">4.2.5 </span><a href="#client-visibilitystate">visibilityState</a></li><li><span class="marker">4.2.6 </span><a href="#client-focused">focused</a></li><li><span class="marker">4.2.7 </span><a href="#client-focus">focus()</a></li><li><span class="marker">4.2.8 </span><a href="#client-navigate">navigate(<var>url</var>)</a></li></ol></li><li><span class="marker">4.3 </span><a href="#clients">Clients</a><ol><li><span class="marker">4.3.1 </span><a href="#clients-getall">matchAll(<var>options</var>)</a></li><li><span class="marker">4.3.2 </span><a href="#clients-openwindow">openWindow(<var>url</var>)</a></li><li><span class="marker">4.3.3 </span><a href="#clients-claim">claim()</a></li></ol></li><li><span class="marker">4.4 </span><a href="#extendable-event">ExtendableEvent</a><ol><li><span class="marker">4.4.1 </span><a href="#wait-until-method">event.waitUntil(<var>f</var>)</a></li></ol></li><li><span class="marker">4.5 </span><a href="#fetch-event-section">FetchEvent</a><ol><li><span class="marker">4.5.1 </span><a href="#fetch-event-request">event.request</a></li><li><span class="marker">4.5.2 </span><a href="#fetch-event-client">event.client</a></li><li><span class="marker">4.5.3 </span><a href="#is-reload-attribute">event.isReload</a></li><li><span class="marker">4.5.4 </span><a href="#respond-with-method">event.respondWith(r)</a></li></ol></li><li><span class="marker">4.6 </span><a href="#extendablemessage-event-section">ExtendableMessageEvent</a><ol><li><span class="marker">4.6.1 </span><a href="#extendablemessage-event-data">event.data</a></li><li><span class="marker">4.6.2 </span><a href="#extendablemessage-event-origin">event.origin</a></li><li><span class="marker">4.6.3 </span><a href="#extendablemessage-event-lasteventid">event.lastEventId</a></li><li><span class="marker">4.6.4 </span><a href="#extendablemessage-event-source">event.source</a></li><li><span class="marker">4.6.5 </span><a href="#extendablemessage-event-ports">event.ports</a></li></ol></li><li><span class="marker">4.7 </span><a href="#execution-context-events">Events</a></li></ol></li><li><span class="marker">5 </span><a href="#cache-objects">Caches</a><ol><li><span class="marker">5.1 </span><a href="#cache-constructs">Constructs</a></li><li><span class="marker">5.2 </span><a href="#cache-lifetimes">Understanding Cache Lifetimes</a></li><li><span class="marker">5.3 </span><a href="#self-caches">self.caches</a><ol><li><span class="marker">5.3.1 </span><a href="#global-caches">caches</a></li></ol></li><li><span class="marker">5.4 </span><a href="#cache">Cache</a><ol><li><span class="marker">5.4.1 </span><a href="#cache-match">match(<var>request</var>, <var>options</var>)</a></li><li><span class="marker">5.4.2 </span><a href="#cache-matchall">matchAll(<var>request</var>, <var>options</var>)</a></li><li><span class="marker">5.4.3 </span><a href="#cache-add">add(<var>request</var>)</a></li><li><span class="marker">5.4.4 </span><a href="#cache-addAll">addAll(<var>requests</var>)</a></li><li><span class="marker">5.4.5 </span><a href="#cache-put">put(<var>request</var>, <var>response</var>)</a></li><li><span class="marker">5.4.6 </span><a href="#cache-delete">delete(<var>request</var>, <var>options</var>)</a></li><li><span class="marker">5.4.7 </span><a href="#cache-keys">keys(<var>request</var>, <var>options</var>)</a></li></ol></li><li><span class="marker">5.5 </span><a href="#cache-storage">CacheStorage</a><ol><li><span class="marker">5.5.1 </span><a href="#cache-storage-match">match(<var>request</var>, <var>options</var>)</a></li><li><span class="marker">5.5.2 </span><a href="#cache-storage-has">has(<var>cacheName</var>)</a></li><li><span class="marker">5.5.3 </span><a href="#cache-storage-open">open(<var>cacheName</var>)</a></li><li><span class="marker">5.5.4 </span><a href="#cache-storage-delete">delete(<var>cacheName</var>)</a></li><li><span class="marker">5.5.5 </span><a href="#cache-storage-keys">keys()</a></li></ol></li></ol></li><li><span class="marker">6 </span><a href="#security-considerations">Security Considerations</a><ol><li><span class="marker">6.1 </span><a href="#origin-relativity">Origin Relativity</a><ol><li><span class="marker">6.1.1 </span><a href="#importscripts">importScripts(<var>urls</var>)</a></li></ol></li><li><span class="marker">6.2 </span><a href="#cross-origin-resources">Cross-Origin Resources and CORS</a></li></ol></li><li><span class="marker">7 </span><a href="#storage-considerations">Storage Considerations</a></li><li><span class="marker">8 </span><a href="#extensibility">Extensibility</a><ol><li><span class="marker">8.1 </span><a href="#extension-to-service-worker-registration">Define API bound to Service Worker Registration</a></li><li><span class="marker">8.2 </span><a href="#extension-to-extendable-event">Define Functional Event</a></li><li><span class="marker">8.3 </span><a href="#extension-to-service-worker-global-scope">Define Event Handler</a></li><li><span class="marker">8.4 </span><a href="#request-functional-event-dispatch">Request Functional Event Dispatch</a></li></ol></li><li><span class="marker">9 </span><a href="#algorithms">Appendix A: Algorithms</a><ol><li><span class="marker">9.1 </span><a href="#register-algorithm">Register</a></li><li><span class="marker">9.2 </span><a href="#update-algorithm">Update</a></li><li><span class="marker">9.3 </span><a href="#soft-update-algorithm">Soft Update</a></li><li><span class="marker">9.4 </span><a href="#installation-algorithm">Install</a></li><li><span class="marker">9.5 </span><a href="#activation-algorithm">Activate</a></li><li><span class="marker">9.6 </span><a href="#run-service-worker-algorithm">Run Service Worker</a></li><li><span class="marker">9.7 </span><a href="#on-fetch-request-algorithm">Handle Fetch</a></li><li><span class="marker">9.8 </span><a href="#handle-functional-event-algorithm">Handle Functional Event</a></li><li><span class="marker">9.9 </span><a href="#on-client-unload-algorithm">Handle Service Worker Client Unload</a></li><li><span class="marker">9.10 </span><a href="#unregister-algorithm">Unregister</a></li><li><span class="marker">9.11 </span><a href="#set-registration-algorithm">Set Registration</a></li><li><span class="marker">9.12 </span><a href="#clear-registration-algorithm">Clear Registration</a></li><li><span class="marker">9.13 </span><a href="#update-state-algorithm">Update State</a></li><li><span class="marker">9.14 </span><a href="#notify-controller-change-algorithm">Notify Controller Change</a></li><li><span class="marker">9.15 </span><a href="#scope-match-algorithm">Match Service Worker Registration</a></li><li><span class="marker">9.16 </span><a href="#get-registration-algorithm">Get Registration</a></li><li><span class="marker">9.17 </span><a href="#get-newest-worker-algorithm">Get Newest Worker</a></li><li><span class="marker">9.18 </span><a href="#capture-windowclient-algorithm">Capture Window Client</a></li><li><span class="marker">9.19 </span><a href="#query-cache-algorithm">Query Cache</a></li><li><span class="marker">9.20 </span><a href="#batch-cache-operations-algorithm">Batch Cache Operations</a></li></ol></li><li><span class="marker">10 </span><a href="#acknowledgements">Acknowledgements</a></li></ol></nav>

<section title="introduction"><header><span class="section-number">1</span> <h2 id="introduction" data-bookmark-label="1 Introduction">Introduction</h2><span class="anchor"><a style="text-decoration: none;" href="#introduction">¶</a></span></header>


  <section title="about"><header><span class="section-number">1.1</span> <h3 id="about" data-bookmark-label="1.1 About this Document">About this Document</h3><span class="anchor"><a style="text-decoration: none;" href="#about">¶</a></span></header>


    <p id="about.1">All diagrams, examples, notes, are non-normative, as well as sections explicitly marked as non-normative. Everything else in this specification is normative.</p>

    <p id="about.2">The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "MAY", and "OPTIONAL" in the normative parts of this document are to be interpreted as described in <a href="http://dev.w3.org/2006/xbl2/#refsRFC2119">RFC2119</a>. For readability, these words do not appear in all uppercase letters in this specification.</p>

    <p id="about.3">Any point, at which a conforming UA must make decisions about the state or reaction to the state of the conceptual model, is captured as <a href="https://en.wikipedia.org/wiki/Algorithm">algorithm</a>. The algorithms are defined in terms of processing equivalence. The <dfn id="dfn-processing-equivalence">processing equivalence</dfn> is a constraint imposed on the algorithm implementers, requiring the output of the both UA-implemented and the specified algorithm to be exactly the same for all inputs.</p>
  </section>

  <section title="dependencies"><header><span class="section-number">1.2</span> <h3 id="dependencies" data-bookmark-label="1.2 Dependencies">Dependencies</h3><span class="anchor"><a style="text-decoration: none;" href="#dependencies">¶</a></span></header>


    <p id="dependencies.1">This document relies on the following specifications:</p>

    <ul>
      <li><a href="http://www.w3.org/TR/workers/">Web Workers</a></li>
      <li><a href="https://fetch.spec.whatwg.org/">Fetch Living Standard</a></li>
      <li><a href="https://dom.spec.whatwg.org/">DOM Living Standard</a></li>
      <li><a href="https://html.spec.whatwg.org/multipage/">HTML Living Standard</a></li>
      <li><a href="http://www.ecma-international.org/ecma-262/6.0/">ECMAScript 2015 Language Specification</a></li>
      <li><a href="http://www.w3.org/TR/WebIDL/">Web IDL</a></li>
      <li><a href="http://www.w3.org/TR/quota-api/">Quota Management API</a></li>
      <li><a href="http://www.w3.org/TR/notifications/">Web Notifications</a></li>
      <li><a href="http://tools.ietf.org/html/rfc6454">The Web Origin Concept</a></li>
      <li><a href="https://url.spec.whatwg.org/">URL Living Standard</a></li>
      <li><a href="https://tools.ietf.org/html/rfc7230">Hypertext Transfer Protocol (HTTP/1.1): Message Syntax and Routing</a></li>
      <li><a href="https://tools.ietf.org/html/rfc7231">Hypertext Transfer Protocol (HTTP/1.1): Semantics and Content</a></li>
      <li><a href="https://w3c.github.io/webappsec/specs/powerfulfeatures/">Requirements for Powerful Features</a></li>
      <li><a href="http://www.w3.org/2001/tag/doc/promises-guide">Writing Promise-Using Specifications</a></li>
      <li><a href="http://www.w3.org/TR/page-visibility/">Page Visibility (Second Edition)</a></li>
      <li><a href="http://tools.ietf.org/html/rfc4122">A Universally Unique IDentifier (UUID) URN Namespace</a></li>
    </ul>
  </section>

  <section title="motivations"><header><span class="section-number">1.3</span> <h3 id="motivations" data-bookmark-label="1.3 Motivations">Motivations</h3><span class="anchor"><a style="text-decoration: none;" href="#motivations">¶</a></span></header>


    <p id="motivations.1">Web Applications traditionally assume that the network is reachable. This assumption pervades the platform. HTML documents are loaded over HTTP and traditionally fetch all of their sub-resources via subsequent HTTP requests. This places web content at a disadvantage versus other technology stacks.</p>

    <p id="motivations.2">The <a href="#dfn-service-worker">service worker</a> is designed first to redress this balance by providing a Web Worker context, which can be started by a runtime when navigations are about to occur. This event-driven worker is registered against an origin and a path (or pattern), meaning it can be consulted when navigations occur to that location. Events that correspond to network requests are dispatched to the worker and the responses generated by the worker may over-ride default network stack behavior. This puts the <a href="#dfn-service-worker">service worker</a>, conceptually, between the network and a document renderer, allowing the <a href="#dfn-service-worker">service worker</a> to provide content for documents, even while offline.</p>

    <p id="motivations.3">Web developers familiar with previous attempts to solve the offline problem have reported a deficit of flexibility in those solutions. As a result, the <a href="#dfn-service-worker">service worker</a> is highly procedural, providing a maximum of flexibility at the price of additional complexity for developers. Part of this complexity arises from the need to keep <a href="#dfn-service-worker">service workers</a> responsive in the face of a single-threaded execution model. As a result, APIs exposed by <a href="#dfn-service-worker">service workers</a> are almost entirely asynchronous, a pattern familiar in other JavaScript contexts but accentuated here by the need to avoid blocking document and resource loading.</p>

    <p id="motivations.4">Developers using the <a href="https://html.spec.whatwg.org/multipage/browsers.html#offline">HTML5 Application Cache</a> have also <a href="http://alistapart.com/article/application-cache-is-a-douchebag">reported that several attributes</a> of the design contribute to <a href="http://alistapart.com/article/application-cache-is-a-douchebag/index.html#section6">unrecoverable errors</a>. A key design principle of the <a href="#dfn-service-worker">service worker</a> is that errors should <em>always</em> be recoverable. Many details of the update process of <a href="#dfn-service-worker">service workers</a> are designed to avoid these hazards.</p>

    <p id="motivations.5"><a href="#dfn-service-worker">Service workers</a> are started and kept alive by their relationship to events, not documents. This design borrows heavily from developer and vendor experience with <a href="http://www.w3.org/TR/workers/#sharedworker">Shared Workers</a> and <a href="https://developer.chrome.com/extensions/background_pages">Chrome Background Pages</a>. A key lesson from these systems is the necessity to time-limit the execution of background processing contexts, both to conserve resources and to ensure that background context loss and restart is top-of-mind for developers. As a result, <a href="#dfn-service-worker">service workers</a> bear more than a passing resemblance to <a href="https://developer.chrome.com/extensions/event_pages">Chrome Event Pages</a>, the successor to Background Pages. <a href="#dfn-service-worker">Service workers</a> may be started by user agents <em>without an attached document</em> and may be killed by the user agent at nearly any time. Conceptually, <a href="#dfn-service-worker">service workers</a> can be thought of as Shared Workers that can start, process events, and die without ever handling messages from documents. Developers are advised to keep in mind that <a href="#dfn-service-worker">service workers</a> may be started and killed many times a second.</p>

    <p id="motivations.6"><a href="#dfn-service-worker">Service workers</a> are generic, event-driven, time-limited script contexts that run at an origin. These properties make them natural endpoints for a range of runtime services that may outlive the context of a particular document, e.g. handling push notifications, background data synchronization, responding to resource requests from other origins, or receiving centralized updates to expensive-to-calculate data (e.g., geolocation or gyroscope).</p>
  </section>
</section>

<section title="model"><header><span class="section-number">2</span> <h2 id="model" data-bookmark-label="2 Model">Model</h2><span class="anchor"><a style="text-decoration: none;" href="#model">¶</a></span></header>


  <section title="service-worker-concept"><header><span class="section-number">2.1</span> <h3 id="service-worker-concept" data-bookmark-label="2.1 Service Worker">Service Worker</h3><span class="anchor"><a style="text-decoration: none;" href="#service-worker-concept">¶</a></span></header>

    <p id="service-worker-concept.1">A <dfn id="dfn-service-worker">service worker</dfn> is a type of <a href="http://www.w3.org/TR/workers/">web worker</a>. A <a href="#dfn-service-worker">service worker</a> executes in the registering <a href="#dfn-service-worker-client">service worker client</a>'s <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a>.</p>
    <p id="service-worker-concept.2">A <a href="#dfn-service-worker">service worker</a> has an associated <dfn id="dfn-state">state</dfn>, which is one of <em>parsed</em>, <em>installing</em>, <em>installed</em>, <em>activating</em>, <em>activated</em>, and <em>redundant</em>. (Initially <em>parsed</em>).</p>
    <p id="service-worker-concept.3">A <a href="#dfn-service-worker">service worker</a> has an associated <dfn id="dfn-script-url">script url</dfn> (a <a href="https://url.spec.whatwg.org/#concept-url">URL</a>).</p>
    <p id="service-worker-concept.4">A <a href="#dfn-service-worker">service worker</a> has an associated <dfn id="dfn-containing-service-worker-registration">containing service worker registration</dfn> (a <a href="#dfn-service-worker-registration">service worker registration</a>), which contains itself.</p>
    <p id="service-worker-concept.5">A <a href="#dfn-service-worker">service worker</a> has an associated <dfn id="dfn-service-worker-id">id</dfn> (a <a href="http://tools.ietf.org/html/rfc4122#section-3">UUID</a>), which uniquely identifies itself during the lifetime of its <a href="#dfn-containing-service-worker-registration">containing service worker registration</a>.</p>
    <p id="service-worker-concept.6">A <a href="#dfn-service-worker">service worker</a> is dispatched a set of <dfn id="dfn-lifecycle-events">lifecycle events</dfn>, <a href="#service-worker-global-scope-install-event">install</a> and <a href="#service-worker-global-scope-activate-event">activate</a>, and <dfn id="dfn-functional-events">functional events</dfn> including <a href="#service-worker-global-scope-fetch-event">fetch</a>.</p>
    <p id="service-worker-concept.7">A <a href="#dfn-service-worker">service worker</a> has an associated <dfn id="dfn-script-resource-map">script resource map</dfn> which is a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-list-and-record-specification-type">List</a> of the <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-list-and-record-specification-type">Record</a> {[[key]], [[value]]} where [[key]] is a <a href="https://url.spec.whatwg.org/#concept-url">URL</a> and [[value]] is a script resource.</p>
    <p id="service-worker-concept.8">A <a href="#dfn-service-worker">service worker</a> has an associated <dfn id="dfn-skip-waiting-flag">skip waiting flag</dfn>. Unless stated otherwise it is unset.</p>
    <p id="service-worker-concept.9">A <a href="#dfn-service-worker">service worker</a> has an associated <dfn id="dfn-imported-scripts-updated-flag">imported scripts updated flag</dfn>. It is initially unset.</p>

    <section title="service-worker-lifetime"><header><span class="section-number">2.1.1</span> <h4 id="service-worker-lifetime" data-bookmark-label="2.1.1 Lifetime">Lifetime</h4><span class="anchor"><a style="text-decoration: none;" href="#service-worker-lifetime">¶</a></span></header>

    <p id="service-worker-lifetime.1">The lifetime of a <a href="#dfn-service-worker">service worker</a> is tied to the execution lifetime of events, not references held by <a href="#dfn-service-worker-client">service worker clients</a> to the <code><a href="#service-worker-interface">ServiceWorker</a></code> object. The user agent <em class="rfc2119" title="MAY">may</em> <a href="https://html.spec.whatwg.org/multipage/workers.html#terminate-a-worker">terminate</a> <a href="#dfn-service-worker">service workers</a> at any time it has no event to handle or detects abnormal operation such as infinite loops and tasks exceeding imposed time limits, if any, while handling the events.</p>
    </section>
  </section>

  <section title="service-worker-registration-concept"><header><span class="section-number">2.2</span> <h3 id="service-worker-registration-concept" data-bookmark-label="2.2 Service Worker Registration">Service Worker Registration</h3><span class="anchor"><a style="text-decoration: none;" href="#service-worker-registration-concept">¶</a></span></header>

    <p id="service-worker-registration-concept.1">A <dfn id="dfn-service-worker-registration">service worker registration</dfn> is a tuple of a <a href="#dfn-scope-url">scope url</a> and a set of <a href="#dfn-service-worker">service workers</a>, an <a href="#dfn-installing-worker">installing worker</a>, a <a href="#dfn-waiting-worker">waiting worker</a>, and an <a href="#dfn-active-worker">active worker</a>. The user agents <em class="rfc2119" title="MAY">may</em> enable many <a href="#dfn-service-worker-registration">service worker registrations</a> at a single origin so long as the <a href="#dfn-scope-url">scope url</a> of the <a href="#dfn-service-worker-registration">service worker registration</a> differs. A <a href="#dfn-service-worker-registration">service worker registration</a> of an identical <a href="#dfn-scope-url">scope url</a> when one already exists in the user agent causes the existing <a href="#dfn-service-worker-registration">service worker registration</a> to be replaced.</p>
    <p id="service-worker-registration-concept.2">A <a href="#dfn-service-worker-registration">service worker registration</a> has an associated <dfn id="dfn-scope-url">scope url</dfn> (a <a href="https://url.spec.whatwg.org/#concept-url">URL</a>).</p>
    <p id="service-worker-registration-concept.3">A <a href="#dfn-service-worker-registration">service worker registration</a> has an associated <dfn id="dfn-registration-script-url">registering script url</dfn> (a <a href="https://url.spec.whatwg.org/#concept-url">URL</a>).</p>
    <p id="service-worker-registration-concept.4">A <a href="#dfn-service-worker-registration">service worker registration</a> has an associated <dfn id="dfn-installing-worker">installing worker</dfn> (a <a href="#dfn-service-worker">service worker</a>) whose <a href="#dfn-state">state</a> is <em>installing</em>. It is initially set to null.</p>
    <p id="service-worker-registration-concept.5">A <a href="#dfn-service-worker-registration">service worker registration</a> has an associated <dfn id="dfn-waiting-worker">waiting worker</dfn> (a <a href="#dfn-service-worker">service worker</a>) whose <a href="#dfn-state">state</a> is <em>installed</em>. It is initially set to null.</p>
    <p id="service-worker-registration-concept.6">A <a href="#dfn-service-worker-registration">service worker registration</a> has an associated <dfn id="dfn-active-worker">active worker</dfn> (a <a href="#dfn-service-worker">service worker</a>) whose <a href="#dfn-state">state</a> is either <em>activating</em> or <em>activated</em>. It is initially set to null. An <a href="#dfn-active-worker">active worker</a> <dfn id="dfn-control">controls</dfn> a <a href="#dfn-service-worker-client">service worker client</a> if the <a href="#dfn-active-worker">active worker</a>'s <a href="#dfn-containing-service-worker-registration">containing service worker registration</a>'s <a href="#dfn-scope-url">scope url</a> <a href="#scope-match-algorithm">matches</a> the <a href="#dfn-service-worker-client">service worker client</a>'s <a href="https://www.w3.org/Bugs/Public/show_bug.cgi?id=27146">creation url</a> upon <a href="https://html.spec.whatwg.org/multipage/browsers.html#navigate">navigation</a>. When a <a href="#dfn-service-worker-client">service worker client</a> is <a href="#dfn-control">controlled</a> by an <a href="#dfn-active-worker">active worker</a>, it is considered the <a href="#dfn-service-worker-client">service worker client</a> is <dfn id="dfn-use">using</dfn> the <a href="#dfn-active-worker">active worker</a>'s <a href="#dfn-containing-service-worker-registration">containing service worker registration</a>.</p>
    <p id="service-worker-registration-concept.7">A <a href="#dfn-service-worker-registration">service worker registration</a> has an associated <dfn id="dfn-uninstalling-flag">uninstalling flag</dfn>. It is initially unset.</p>

    <section title="service-worker-registration-lifetime"><header><span class="section-number">2.2.1</span> <h4 id="service-worker-registration-lifetime" data-bookmark-label="2.2.1 Lifetime">Lifetime</h4><span class="anchor"><a style="text-decoration: none;" href="#service-worker-registration-lifetime">¶</a></span></header>

    <p id="service-worker-registration-lifetime.1">The user agents <em class="rfc2119" title="MUST">must</em> persistently keep a list of <a href="#register-algorithm">registered</a> <a href="#dfn-service-worker-registration">service worker registrations</a> unless otherwise they are explicitly <a href="#unregister-algorithm">unregistered</a>. The user agent has a <a href="#dfn-scope-to-registration-map">scope to registration map</a> that stores the entries of the tuple of <a href="#dfn-service-worker-registration">service worker registration</a>'s <a href="#dfn-scope-url">scope url</a> and the corresponding <a href="#dfn-service-worker-registration">service worker registration</a>. The lifetime of <a href="#dfn-service-worker-registration">service worker registrations</a> is beyond that of the <code><a href="#service-worker-registration-interface">ServiceWorkerRegistration</a></code> objects which represent them within the lifetime of their corresponding <a href="#dfn-service-worker-client">service worker clients</a>.</p>
    </section>
  </section>
  <section title="service-worker-client-concept"><header><span class="section-number">2.3</span> <h3 id="service-worker-client-concept" data-bookmark-label="2.3 Service Worker Client">Service Worker Client</h3><span class="anchor"><a style="text-decoration: none;" href="#service-worker-client-concept">¶</a></span></header>

    <p id="service-worker-client-concept.1">A <dfn id="dfn-service-worker-client">service worker client</dfn> is an <a href="https://html.spec.whatwg.org/multipage/webappapis.html#environment-settings-object">environment settings object</a> that specifies various settings for its <a href="https://html.spec.whatwg.org/multipage/infrastructure.html#javascript-global-environment">JavaScript global environment</a>. A <a href="#dfn-service-worker-client">service worker client</a> independently <a href="#scope-match-algorithm">selects</a> and <a href="#dfn-use">uses</a> a <a href="#dfn-service-worker-registration">service worker registration</a> for its own loading and its subresources.</p>

    <p id="service-worker-client-concept.2">A <a href="#dfn-service-worker-client">service worker client</a> has an associated <dfn id="dfn-service-worker-client-active-worker">active worker</dfn> (an <a href="#dfn-active-worker">active worker</a>) which currently <a href="#dfn-control">controls</a> it. It is initially set to null.</p>

    <p id="service-worker-client-concept.3">A <a href="#dfn-service-worker-client">service worker client</a> has an associated <dfn id="dfn-service-worker-client-id">id</dfn> (a <a href="http://tools.ietf.org/html/rfc4122#section-3">UUID</a>), which uniquely identifies itself during its lifetime. It is initially set to a new <a href="http://tools.ietf.org/html/rfc4122#section-3">UUID</a> when the corresponding <a href="https://html.spec.whatwg.org/multipage/webappapis.html#environment-settings-object">environment settings object</a> that it represents is created.</p>

    <p id="service-worker-client-concept.4">A <dfn id="dfn-window-client">window client</dfn> is a <a href="#dfn-service-worker-client">service worker client</a> whose <a href="https://html.spec.whatwg.org/multipage/webappapis.html#global-object">global object</a> is a <a href="https://html.spec.whatwg.org/multipage/browsers.html#window">Window</a> object.</p>

    <p id="service-worker-client-concept.5">A <a href="#dfn-window-client">window client</a> has an associated <dfn id="dfn-window-client-frametype">frame type</dfn> (a <a href="https://fetch.spec.whatwg.org/#concept-request-context-frame-type">context frame type</a>).</p>

    <p id="service-worker-client-concept.6">A <dfn id="dfn-dedicatedworker-client">dedicated worker client</dfn> is a <a href="#dfn-service-worker-client">service worker client</a> whose <a href="https://html.spec.whatwg.org/multipage/webappapis.html#global-object">global object</a> is a <a href="https://html.spec.whatwg.org/multipage/workers.html#dedicatedworkerglobalscope">DedicatedWorkerGlobalObject</a> object.</p>

    <p id="service-worker-client-concept.7">A <dfn id="dfn-sharedworker-client">shared worker client</dfn> is a <a href="#dfn-service-worker-client">service worker client</a> whose <a href="https://html.spec.whatwg.org/multipage/webappapis.html#global-object">global object</a> is a <a href="https://html.spec.whatwg.org/multipage/workers.html#sharedworkerglobalscope">SharedWorkerGlobalObject</a> object.</p>

    <p id="service-worker-client-concept.8">A <dfn id="dfn-worker-client">worker client</dfn> is either a <a href="#dfn-dedicatedworker-client">dedicated worker client</a> or a <a href="#dfn-sharedworker-client">shared worker client</a>.</p>
  </section>
</section>

<section title="document-context"><header><span class="section-number">3</span> <h2 id="document-context" data-bookmark-label="3 Client Context">Client Context</h2><span class="anchor"><a style="text-decoration: none;" href="#document-context">¶</a></span></header>


  <p id="document-context.1">Example: Bootstrapping with a ServiceWorker</p>

<pre><code>// scope defaults to the path the script sits in
// "/" in this example
navigator.serviceWorker.register("/serviceworker.js").then(
  function(registration) {
    console.log("success!");
    if (registration.installing) {
      registration.installing.postMessage("Howdy from your installing page.");
    }
  },
  function(why) {
    console.error("Installing the worker failed!:", why);
  });</code></pre>

  <section title="service-worker-obj"><header><span class="section-number">3.1</span> <h3 id="service-worker-obj" data-bookmark-label="3.1 ServiceWorker"><code>ServiceWorker</code></h3><span class="anchor"><a style="text-decoration: none;" href="#service-worker-obj">¶</a></span></header>


    <p id="service-worker-obj.1"></p>
<pre><code>[Exposed=(Window,Worker)]
interface <dfn id="service-worker-interface" title="ServiceWorker">ServiceWorker</dfn> : <a href="https://dom.spec.whatwg.org/#eventtarget">EventTarget</a> {
  readonly attribute <a href="http://heycam.github.io/webidl/#idl-USVString">USVString</a> <a href="#service-worker-url-attribute">scriptURL</a>;
  readonly attribute <a href="#service-worker-state-enum">ServiceWorkerState</a> <a href="#service-worker-state-attribute">state</a>;
  readonly attribute DOMString <a href="#service-worker-id-attribute">id</a>;
  void <a href="#service-worker-postmessage-method">postMessage</a>(any <var>message</var>, optional sequence&lt;<a href="https://html.spec.whatwg.org/multipage/infrastructure.html#transferable">Transferable</a>&gt; <var>transfer</var>);

  // event
  attribute <a href="https://html.spec.whatwg.org/multipage/webappapis.html#eventhandler">EventHandler</a> <a href="#service-worker-onstatechange-attribute">onstatechange</a>;
};
<code><a href="#service-worker-interface">ServiceWorker</a></code> implements <a href="https://html.spec.whatwg.org/multipage/workers.html#abstractworker">AbstractWorker</a>;

enum <dfn id="service-worker-state-enum" title="State">ServiceWorkerState</dfn> {
  "installing",
  "installed",
  "activating",
  "activated",
  "redundant"
};</code></pre>

    <p id="service-worker-obj.2">A <code><a href="#service-worker-interface">ServiceWorker</a></code> object represents a <a href="#dfn-service-worker">service worker</a>. Each <code><a href="#service-worker-interface">ServiceWorker</a></code> object is associated with a <a href="#dfn-service-worker">service worker</a>. Multiple separate objects implementing the <code><a href="#service-worker-interface">ServiceWorker</a></code> interface across <a href="https://html.spec.whatwg.org/multipage/webappapis.html#document-environment">document environments</a> and <a href="https://html.spec.whatwg.org/multipage/webappapis.html#worker-environment">worker environments</a> can all be associated with the same <a href="#dfn-service-worker">service worker</a> simultaneously.</p>

    <p id="service-worker-obj.3">A <code><a href="#service-worker-interface">ServiceWorker</a></code> object has an associated <code><a href="#service-worker-state-enum">ServiceWorkerState</a></code> object which is itself associated with <a href="#dfn-service-worker">service worker</a>'s <a href="#dfn-state">state</a>.</p>

    <p id="service-worker-obj.4">A <code><a href="#service-worker-interface">ServiceWorker</a></code> object has an associated <dfn id="dfn-service-worker-interface-client">service worker client</dfn> (a <a href="#dfn-service-worker-client">service worker client</a>).</p>

    <section title="service-worker-url"><header><span class="section-number">3.1.1</span> <h4 id="service-worker-url" data-bookmark-label="3.1.1 scriptURL"><code>scriptURL</code></h4><span class="anchor"><a style="text-decoration: none;" href="#service-worker-url">¶</a></span></header>


      <p id="service-worker-url.1">The <dfn id="service-worker-url-attribute"><code>scriptURL</code></dfn> attribute <em class="rfc2119" title="MUST">must</em> return the <a href="#dfn-service-worker">service worker</a>'s <a href="https://url.spec.whatwg.org/#concept-url-serializer">serialized</a> <a href="#dfn-script-url">script url</a>.</p>

      <p id="service-worker-url.2">For example, consider a document created by a navigation to <code>https://example.com/app.html</code> which <a href="#on-fetch-request-algorithm">matches</a> via the following registration call which has been previously executed:</p>

<pre><code>// Script on the page https://example.com/app.html
navigator.serviceWorker.register("/service_worker.js", { scope: "/" });</code></pre>

      <p id="service-worker-url.3">The value of <code>navigator.serviceWorker.controller.scriptURL</code> will be "<code>https://example.com/service_worker.js</code>".</p>
    </section>

    <section title="service-worker-state"><header><span class="section-number">3.1.2</span> <h4 id="service-worker-state" data-bookmark-label="3.1.2 state"><code>state</code></h4><span class="anchor"><a style="text-decoration: none;" href="#service-worker-state">¶</a></span></header>


      <p id="service-worker-state.1">The <dfn id="service-worker-state-attribute"><code>state</code></dfn> attribute <em class="rfc2119" title="MUST">must</em> return the value (in <a href="#service-worker-state-enum">ServiceWorkerState</a> enumeration) corresponding to the first matching statement, switching on the <a href="#dfn-service-worker">service worker</a>'s <a href="#dfn-state">state</a>:</p>

      <dl>
        <dt><em>installing</em></dt>
        <dd>"<code>installing</code>"
        <p class="note">The <a href="#dfn-service-worker">service worker</a> in this state is considered an <a href="#dfn-installing-worker">installing worker</a>. During this state, <code><a href="#extendable-event-waituntil-method">event.waitUntil(<var>f</var>)</a></code> can be called inside the <code><a href="#service-worker-global-scope-oninstall-attribute">oninstall</a></code> <a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-handlers">event handler</a> to extend the life of the <a href="#dfn-installing-worker">installing worker</a> until the passed <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> resolves successfully. This is primarily used to ensure that the <a href="#dfn-service-worker">service worker</a> is not active until all of the core caches are populated.</p></dd>

        <dt><em>installed</em></dt>
        <dd>"<code>installed</code>"
        <p class="note">The <a href="#dfn-service-worker">service worker</a> in this state is considered a <a href="#dfn-waiting-worker">waiting worker</a>.</p></dd>

        <dt><em>activating</em></dt>
        <dd>"<code>activating</code>"
        <p class="note">The <a href="#dfn-service-worker">service worker</a> in this state is considered an <a href="#dfn-active-worker">active worker</a>. During this state, <code><a href="#extendable-event-waituntil-method">event.waitUntil(<var>f</var>)</a></code> can be called inside the <code><a href="#service-worker-global-scope-onactivate-attribute">onactivate</a></code> <a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-handlers">event handler</a> to extend the life of the <a href="#dfn-active-worker">active worker</a> until the passed <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> resolves successfully. No <a href="#dfn-functional-events">functional events</a> are dispatched until the state becomes <em>activated</em>.</p></dd>

        <dt><em>activated</em></dt>
        <dd>"<code>activated</code>"
        <p class="note">The <a href="#dfn-service-worker">service worker</a> in this state is considered an <a href="#dfn-active-worker">active worker</a> ready to handle <a href="#dfn-functional-events">functional events</a>.</p></dd>

        <dt><em>redundant</em></dt>
        <dd>"<code>redundant</code>"
        <p class="note">A new <a href="#dfn-service-worker">service worker</a> is replacing the current <a href="#dfn-service-worker">service worker</a>, or the current <a href="#dfn-service-worker">service worker</a> is being discarded due to an install failure.</p></dd>
      </dl>
    </section>

    <section title="service-worker-id"><header><span class="section-number">3.1.3</span> <h4 id="service-worker-id" data-bookmark-label="3.1.3 id"><code>id</code></h4><span class="anchor"><a style="text-decoration: none;" href="#service-worker-id">¶</a></span></header>


      <p id="service-worker-id.1">The <dfn id="service-worker-id-attribute"><code>id</code></dfn> attribute <em class="rfc2119" title="MUST">must</em> return the <a href="#dfn-service-worker">service worker</a>'s <a href="#dfn-service-worker-id">id</a>.</p>
    </section>

    <section title="service-worker-postmessage"><header><span class="section-number">3.1.4</span> <h4 id="service-worker-postmessage" data-bookmark-label="3.1.4 postMessage(message, transfer)"><code>postMessage(<var>message</var>, <var>transfer</var>)</code></h4><span class="anchor"><a style="text-decoration: none;" href="#service-worker-postmessage">¶</a></span></header>


      <p id="service-worker-postmessage.1">The <dfn id="service-worker-postmessage-method"><code>postMessage(<var>message</var>, <var>transfer</var>)</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>
      <div class="algorithm">
      <ol>
        <li>If the <a href="#service-worker-state-attribute">state</a> attribute value of the <a href="https://dom.spec.whatwg.org/#context-object">context object</a> is "<code>redundant</code>", <a href="http://heycam.github.io/webidl/#dfn-throw">throw</a> an "<code><a href="http://heycam.github.io/webidl/#invalidstateerror">InvalidStateError</a></code>" exception and abort these steps. </li>
        <li>Let <var>newPorts</var> be an empty array.</li>
        <li>Let <var>transferMap</var> be an empty association list of <a href="https://html.spec.whatwg.org/multipage/infrastructure.html#transferable">Transferable</a> objects to placeholder objects.</li>
        <li>If the method was invoked with a second argument <var>transfer</var>, run these substeps:
          <ol>
            <li>If any object is listed in <var>transfer</var> more than once, or any of the <a href="https://html.spec.whatwg.org/multipage/infrastructure.html#transferable">Transferable</a> objects listed in <var>transfer</var> are marked as <a href="https://html.spec.whatwg.org/multipage/infrastructure.html#concept-transferable-neutered">neutered</a>, then <a href="http://heycam.github.io/webidl/#dfn-throw">throw</a> a "<code><a href="http://heycam.github.io/webidl/#datacloneerror">DataCloneError</a></code>" exception and abort these steps.</li>
            <li>For each object <var>x</var> in <var>transfer</var> in turn, add a mapping from <var>x</var> to a new unique placeholder object created for <var>x</var> to <var>transferMap</var>, and if <var>x</var> is a <a href="https://html.spec.whatwg.org/multipage/comms.html#messageport">MessagePort</a> object, also append the placeholder object to <var>newPorts</var>.</li>
          </ol>
        </li>
        <li>Let <var>clonedMessage</var> be a <a href="https://html.spec.whatwg.org/multipage/infrastructure.html#structured-clone">structured clone</a> of <var>message</var> with <var>transferMap</var> as the <var>transferMap</var>. If this <a href="http://heycam.github.io/webidl/#dfn-throw">throws</a> an exception, <a href="http://heycam.github.io/webidl/#dfn-throw">rethrow</a> that exception and abort these steps.</li>
        <li>Let <var>serviceWorker</var> be the <a href="#dfn-service-worker">service worker</a> represented by the <a href="https://dom.spec.whatwg.org/#context-object">context object</a>.</li>
        <li>Invoke <a href="#run-service-worker-algorithm">Run Service Worker</a> algorithm with <var>serviceWorker</var> as the arguement.</li>
        <li>Let <var>destination</var> be the <code><a href="#service-worker-global-scope-interface">ServiceWorkerGlobalScope</a></code> object associated with <var>serviceWorker</var>.</li>
        <li>If the method was invoked with a second argument <var>transfer</var>, run these substeps:
          <ol>
            <li>Let <var>newOwner</var> be the <var>destination</var>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#environment-settings-object">environment settings object</a>.</li>
            <li>For each object <var>x</var> in <var>transfer</var> in turn, obtain a new object <var>y</var> by <a href="https://html.spec.whatwg.org/multipage/infrastructure.html#transfer-a-transferable-object">transferring</a> the object <var>x</var> to <var>newOwner</var>, and replace the placeholder object that was created for the object <var>x</var> by the new object <var>y</var> wherever the placeholder exists (i.e. in <var>clonedMessage</var> and in <var>newPorts</var>).</li>
          </ol>
        </li>
        <li>Make <var>newPorts</var> into a <a href="https://html.spec.whatwg.org/multipage/infrastructure.html#dfn-read-only-array">read only</a> array.</li>
        <li><a href="https://html.spec.whatwg.org/multipage/webappapis.html#queue-a-task">Queue a task</a> that runs the following steps:
          <ol>
            <li>Create an event <var>e</var> that uses the <code><a href="#extendablemessage-event-interface">ExtendableMessageEvent</a></code> interface, with the event type <a href="#service-worker-global-scope-message-event">message</a>, which does not bubble, is not cancelable, and has no default action.</li>
            <li>Let the <a href="https://html.spec.whatwg.org/multipage/comms.html#dom-messageevent-data">data</a> attribute of <var>e</var> be initialized to <var>clonedMessage</var>.</li>
            <li>Let the <a href="https://html.spec.whatwg.org/multipage/comms.html#dom-messageevent-origin">origin</a> attribute of <var>e</var> be initialized to the <a href="https://html.spec.whatwg.org/multipage/browsers.html#unicode-serialisation-of-an-origin">Unicode serialisation</a> of the <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a> specified by the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#incumbent-settings-object">incumbent settings object</a>.</li>
            <li>If the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#global-object">global object</a> <var>globalObject</var> specified by the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#incumbent-settings-object">incumbent settings object</a> is a <code><a href="#service-worker-global-scope-interface">ServiceWorkerGlobalScope</a></code> object, let the <a href="https://html.spec.whatwg.org/multipage/comms.html#dom-messageevent-source">source</a> attribute of <var>e</var> be initialized to a new <code><a href="#service-worker-interface">ServiceWorker</a></code> object that represents <var>globalObject</var>'s <a href="#dfn-service-worker-global-scope-service-worker">service worker</a>.</li>
            <li>Else if <var>globalObject</var> is a <a href="https://html.spec.whatwg.org/multipage/browsers.html#window">Window</a> object, let the <a href="https://html.spec.whatwg.org/multipage/comms.html#dom-messageevent-source">source</a> attribute of <var>e</var> be initialized to a new <code><a href="#window-client-interface">WindowClient</a></code> object that represents <var>globalObject</var>'s <a href="https://html.spec.whatwg.org/multipage/browsers.html#browsing-context">browsing context</a>.</li>
            <li>Else, let it be initialized to a new <code><a href="#client-interface">Client</a></code> object that represents <var>globalObject</var>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#worker-environment">worker environment</a>.</li>
            <li>Let the <a href="https://html.spec.whatwg.org/multipage/comms.html#dom-messageevent-ports">ports</a> attribute of <var>e</var> be initialized to <var>newPorts</var>.</li>
            <li><a href="https://html.spec.whatwg.org/multipage/infrastructure.html#concept-event-dispatch">Dispatch</a> <var>e</var> at <var>destination</var>.</li>
          </ol>
          <p>The <a href="https://html.spec.whatwg.org/multipage/webappapis.html#concept-task">task</a> <em class="rfc2119" title="MUST">must</em> use the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#dom-manipulation-task-source">DOM manipulation task source</a>.</p>
        </li>
      </ol>
      </div>
    </section>

    <section title="service-worker-event-handler"><header><span class="section-number">3.1.5</span> <h4 id="service-worker-event-handler" data-bookmark-label="3.1.5 Event handler">Event handler</h4><span class="anchor"><a style="text-decoration: none;" href="#service-worker-event-handler">¶</a></span></header>


      <p id="service-worker-event-handler.1">The following is the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-handlers">event handler</a> (and its corresponding <a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-handler-event-type">event handler event type</a>) that <em class="rfc2119" title="MUST">must</em> be supported, as <a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-handler-idl-attributes">event handler IDL attributes</a>, by all objects implementing <code><a href="#service-worker-interface">ServiceWorker</a></code> interface:</p>

      <table>
        <thead>
          <tr>
            <th><a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-handlers">event handler</a></th>
            <th><a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-handler-event-type">event handler event type</a></th>
          </tr>
        </thead>
        <tbody>
          <tr>
            <td><dfn id="service-worker-onstatechange-attribute"><code>onstatechange</code></dfn></td>
            <td><code><a href="#service-worker-statechange-event">statechange</a></code></td>
          </tr>
        </tbody>
      </table>
    </section>
  </section>

  <section title="service-worker-registration-obj"><header><span class="section-number">3.2</span> <h3 id="service-worker-registration-obj" data-bookmark-label="3.2 ServiceWorkerRegistration"><code>ServiceWorkerRegistration</code></h3><span class="anchor"><a style="text-decoration: none;" href="#service-worker-registration-obj">¶</a></span></header>


<pre><code>[Exposed=(Window,Worker)]
interface <dfn id="service-worker-registration-interface" title="ServiceWorkerRegistration">ServiceWorkerRegistration</dfn> : <a href="https://dom.spec.whatwg.org/#eventtarget">EventTarget</a> {
  [Unforgeable, SameObject] readonly attribute <a href="#service-worker-interface">ServiceWorker</a>? <a href="#service-worker-registration-installing-attribute">installing</a>;
  [Unforgeable, SameObject] readonly attribute <a href="#service-worker-interface">ServiceWorker</a>? <a href="#service-worker-registration-waiting-attribute">waiting</a>;
  [Unforgeable, SameObject] readonly attribute <a href="#service-worker-interface">ServiceWorker</a>? <a href="#service-worker-registration-active-attribute">active</a>;

  readonly attribute <a href="http://heycam.github.io/webidl/#idl-USVString">USVString</a> <a href="#service-worker-registration-scope-attribute">scope</a>;

  void <a href="#service-worker-registration-update-method">update</a>();
  [NewObject] <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;boolean&gt; <a href="#service-worker-registration-unregister-method">unregister</a>();

  // event
  attribute <a href="https://html.spec.whatwg.org/multipage/webappapis.html#eventhandler">EventHandler</a> <a href="#service-worker-registration-onupdatefound-attribute">onupdatefound</a>;
};</code></pre>

    <p id="service-worker-registration-obj.1">A <code><a href="#service-worker-registration-interface">ServiceWorkerRegistration</a></code> object represents a <a href="#dfn-service-worker-registration">service worker registration</a>. Each <code><a href="#service-worker-registration-interface">ServiceWorkerRegistration</a></code> object is associated with a <dfn id="dfn-service-worker-registration-interface-service-worker-registration">service worker registration</dfn> (a <a href="#dfn-service-worker-registration">service worker registration</a>). Multiple separate objects implementing the <code><a href="#service-worker-registration-interface">ServiceWorkerRegistration</a></code> interface across <a href="https://html.spec.whatwg.org/multipage/webappapis.html#document-environment">document environments</a> and <a href="https://html.spec.whatwg.org/multipage/webappapis.html#worker-environment">worker environments</a> can all be associated with the same <a href="#dfn-service-worker-registration">service worker registration</a> simultaneously.</p>

    <p id="service-worker-registration-obj.2">A <code><a href="#service-worker-registration-interface">ServiceWorkerRegistration</a></code> object has an associated <dfn id="dfn-service-worker-registration-interface-client">service worker client</dfn> (a <a href="#dfn-service-worker-client">service worker client</a>).</p>

    <section title="navigator-service-worker-installing"><header><span class="section-number">3.2.1</span> <h4 id="navigator-service-worker-installing" data-bookmark-label="3.2.1 installing"><code>installing</code></h4><span class="anchor"><a style="text-decoration: none;" href="#navigator-service-worker-installing">¶</a></span></header>


      <p id="navigator-service-worker-installing.1"><dfn id="service-worker-registration-installing-attribute"><code>installing</code></dfn> attribute <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>

      <div class="algorithm">
      <ol>
        <li>Let <var>installingWorker</var> be a <code><a href="#service-worker-interface">ServiceWorker</a></code> object that represents the <a href="#dfn-service-worker-registration-interface-service-worker-registration">service worker registration</a>'s <a href="#dfn-installing-worker">installing worker</a>.</li>
        <li>Set <var>installingWorker</var>'s <a href="#dfn-service-worker-interface-client">service worker client</a> to the <a href="#dfn-service-worker-registration-interface-client">service worker client</a>.</li>
        <li>Return <var>installingWorker</var>.</li>
      </ol>
      </div>
    </section>

    <section title="navigator-service-worker-waiting"><header><span class="section-number">3.2.2</span> <h4 id="navigator-service-worker-waiting" data-bookmark-label="3.2.2 waiting"><code>waiting</code></h4><span class="anchor"><a style="text-decoration: none;" href="#navigator-service-worker-waiting">¶</a></span></header>


      <p id="navigator-service-worker-waiting.1"><dfn id="service-worker-registration-waiting-attribute"><code>waiting</code></dfn> attribute <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>

      <div class="algorithm">
      <ol>
        <li>Let <var>waitingWorker</var> be a <code><a href="#service-worker-interface">ServiceWorker</a></code> object that represents the <a href="#dfn-service-worker-registration-interface-service-worker-registration">service worker registration</a>'s <a href="#dfn-waiting-worker">waiting worker</a>.</li>
        <li>Set <var>waitingWorker</var>'s <a href="#dfn-service-worker-interface-client">service worker client</a> to the <a href="#dfn-service-worker-registration-interface-client">service worker client</a>.</li>
        <li>Return <var>waitingWorker</var>.</li>
      </ol>
      </div>
    </section>

    <section title="navigator-service-worker-active"><header><span class="section-number">3.2.3</span> <h4 id="navigator-service-worker-active" data-bookmark-label="3.2.3 active"><code>active</code></h4><span class="anchor"><a style="text-decoration: none;" href="#navigator-service-worker-active">¶</a></span></header>


      <p id="navigator-service-worker-active.1"><dfn id="service-worker-registration-active-attribute"><code>active</code></dfn> attribute <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>

      <div class="algorithm">
      <ol>
        <li>Let <var>activeWorker</var> be a <code><a href="#service-worker-interface">ServiceWorker</a></code> object that represents the <a href="#dfn-service-worker-registration-interface-service-worker-registration">service worker registration</a>'s <a href="#dfn-active-worker">active worker</a>.</li>
        <li>Set <var>activeWorker</var>'s <a href="#dfn-service-worker-interface-client">service worker client</a> to the <a href="#dfn-service-worker-registration-interface-client">service worker client</a>.</li>
        <li>Return <var>activeWorker</var>.</li>
      </ol>
      </div>
    </section>

    <section title="service-worker-registration-scope"><header><span class="section-number">3.2.4</span> <h4 id="service-worker-registration-scope" data-bookmark-label="3.2.4 scope"><code>scope</code></h4><span class="anchor"><a style="text-decoration: none;" href="#service-worker-registration-scope">¶</a></span></header>


      <p id="service-worker-registration-scope.1">The <dfn id="service-worker-registration-scope-attribute"><code>scope</code></dfn> attribute <em class="rfc2119" title="MUST">must</em> return <a href="#dfn-service-worker-registration-interface-service-worker-registration">service worker registration</a>'s <a href="https://url.spec.whatwg.org/#concept-url-serializer">serialized</a> <a href="#dfn-scope-url">scope url</a>.</p>

      <p id="service-worker-registration-scope.2">In the example in section 3.1.1, the value of <code>registration.scope</code>, obtained from <code>navigator.serviceWorker.ready.then(function(registration) { console.log(registration.scope); })</code> for example, will be "<code>https://example.com/</code>".</p>
    </section>

    <section title="service-worker-registration-update"><header><span class="section-number">3.2.5</span> <h4 id="service-worker-registration-update" data-bookmark-label="3.2.5 update()"><code>update()</code></h4><span class="anchor"><a style="text-decoration: none;" href="#service-worker-registration-update">¶</a></span></header>


      <p class="note" id="service-worker-registration-update.1"><code>update()</code> pings the server for an updated version of this script without consulting caches. This is conceptually the same operation that UA does maximum once per every 24 hours.</p>
      <p id="service-worker-registration-update.2"><dfn id="service-worker-registration-update-method"><code>update()</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>
      <div class="algorithm">
      <ol>
        <li>Let <var>registration</var> be the <a href="#dfn-service-worker-registration-interface-service-worker-registration">service worker registration</a>.</li>
        <li>If <var>registration</var>'s <a href="#dfn-uninstalling-flag">uninstalling flag</a> is set, abort these steps.</li>
        <li>If <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a> is not null, abort these steps.</li>
        <li>Let <var>newestWorker</var> be the result of running <a href="#get-newest-worker-algorithm">Get Newest Worker</a> algorithm passing <var>registration</var> as its argument.</li>
        <li>If <var>newestWorker</var> is null, abort these steps.</li>
        <li>Set <var>registration</var>'s <a href="#dfn-registration-script-url">registering script url</a> to <var>newestWorker</var>'s <a href="#dfn-script-url">script url</a>.</li>
        <li>Invoke <a href="#update-algorithm">Update</a> algorithm, or its <a href="#dfn-processing-equivalence">equivalent</a>, passing the <a href="#dfn-service-worker-registration-interface-client">service worker client</a> <var>client</var> and <var>registration</var> as the arguments.</li>
      </ol>
      </div>
    </section>

    <section title="navigator-service-worker-unregister"><header><span class="section-number">3.2.6</span> <h4 id="navigator-service-worker-unregister" data-bookmark-label="3.2.6 unregister()"><code>unregister()</code></h4><span class="anchor"><a style="text-decoration: none;" href="#navigator-service-worker-unregister">¶</a></span></header>


      <p class="note" id="navigator-service-worker-unregister.1">The <code><a href="#service-worker-registration-unregister-method">unregister()</a></code> method unregisters the <a href="#dfn-service-worker-registration">service worker registration</a>. It is important to note that the currently <a href="#dfn-control">controlled</a> <a href="#dfn-service-worker-client">service worker client</a>'s <a href="#dfn-service-worker-client-active-worker">active worker</a>'s <a href="#dfn-containing-service-worker-registration">containing service worker registration</a> is effective until all the <a href="#dfn-service-worker-client">service worker clients</a> (including itself) using this <a href="#dfn-service-worker-registration">service worker registration</a> unload. That is, the <code><a href="#service-worker-registration-unregister-method">unregister()</a></code> method only affects subsequent <a href="https://html.spec.whatwg.org/multipage/browsers.html#navigate">navigations</a>.</p>

      <p id="navigator-service-worker-unregister.2"><dfn id="service-worker-registration-unregister-method"><code>unregister()</code></dfn> method <em class="rfc2119" title="MUST">must</em> return the result of running these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>

      <div class="algorithm">
      <ol>
        <li>Let <var>scopeURL</var> be the <a href="#dfn-scope-url">scope url</a> of the <a href="#dfn-service-worker-registration-interface-service-worker-registration">service worker registration</a>.</li>
          <li>Return the result of running the <a href="#unregister-algorithm">Unregister</a> algorithm, or its <a href="#dfn-processing-equivalence">equivalent</a>, passing the <a href="#dfn-service-worker-registration-interface-client">service worker client</a> <var>client</var>, and <var>scopeURL</var> as the arguments.</li>
      </ol>
      </div>
    </section>

    <section title="service-worker-registration-event-handler"><header><span class="section-number">3.2.7</span> <h4 id="service-worker-registration-event-handler" data-bookmark-label="3.2.7 Event handler">Event handler</h4><span class="anchor"><a style="text-decoration: none;" href="#service-worker-registration-event-handler">¶</a></span></header>


      <p id="service-worker-registration-event-handler.1">The following is the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-handlers">event handler</a> (and its corresponding <a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-handler-event-type">event handler event type</a>) that <em class="rfc2119" title="MUST">must</em> be supported, as <a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-handler-idl-attributes">event handler IDL attributes</a>, by all objects implementing <code><a href="#service-worker-registration-interface">ServiceWorkerRegistration</a></code> interface:</p>

      <table>
        <thead>
          <tr>
            <th><a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-handlers">event handler</a></th>
            <th><a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-handler-event-type">event handler event type</a></th>
          </tr>
        </thead>
        <tbody>
          <tr>
            <td><dfn id="service-worker-registration-onupdatefound-attribute"><code>onupdatefound</code></dfn></td>
            <td><code><a href="#service-worker-registration-updatefound-event">updatefound</a></code></td>
          </tr>
        </tbody>
      </table>
    </section>
  </section>

  <section title="navigator-service-worker"><header><span class="section-number">3.3</span> <h3 id="navigator-service-worker" data-bookmark-label="3.3 navigator.serviceWorker"><code>navigator.serviceWorker</code></h3><span class="anchor"><a style="text-decoration: none;" href="#navigator-service-worker">¶</a></span></header>


<pre><code>partial interface <a href="https://html.spec.whatwg.org/multipage/webappapis.html#navigator">Navigator</a> {
  [SameObject] readonly attribute <a href="#service-worker-container-interface">ServiceWorkerContainer</a> <a href="#navigator-service-worker-attribute">serviceWorker</a>;
};

partial interface <a href="https://html.spec.whatwg.org/multipage/workers.html#workernavigator">WorkerNavigator</a> {
  [SameObject] readonly attribute <a href="#service-worker-container-interface">ServiceWorkerContainer</a> <a href="#navigator-service-worker-attribute">serviceWorker</a>;
};</code></pre>

    <p id="navigator-service-worker.1">The <dfn id="navigator-service-worker-attribute"><code>serviceWorker</code></dfn> attribute <em class="rfc2119" title="MUST">must</em> return the <code><a href="#service-worker-container-interface">ServiceWorkerContainer</a></code> object for the <a href="https://dom.spec.whatwg.org/#context-object">context object</a>.</p>
  </section>

  <section title="service-worker-container"><header><span class="section-number">3.4</span> <h3 id="service-worker-container" data-bookmark-label="3.4 ServiceWorkerContainer"><code>ServiceWorkerContainer</code></h3><span class="anchor"><a style="text-decoration: none;" href="#service-worker-container">¶</a></span></header>


<pre><code>[Exposed=(Window,Worker)]
interface <dfn id="service-worker-container-interface" title="ServiceWorkerContainer">ServiceWorkerContainer</dfn> : <a href="https://dom.spec.whatwg.org/#eventtarget">EventTarget</a> {
  [Unforgeable, SameObject] readonly attribute <a href="#service-worker-interface">ServiceWorker</a>? <a href="#service-worker-container-controller-attribute">controller</a>;
  [SameObject] readonly attribute <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;<a href="#service-worker-registration-interface">ServiceWorkerRegistration</a>&gt; <a href="#service-worker-container-ready-attribute">ready</a>;

  [NewObject] <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;<a href="#service-worker-registration-interface">ServiceWorkerRegistration</a>&gt; <a href="#service-worker-container-register-method">register</a>(<a href="http://heycam.github.io/webidl/#idl-USVString">USVString</a> <var>scriptURL</var>, optional <a href="#registration-option-list-dictionary">RegistrationOptions</a> <var>options</var>);

  [NewObject] <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;<a href="#service-worker-registration-interface">ServiceWorkerRegistration</a>&gt; <a href="#service-worker-container-getregistration-method">getRegistration</a>(optional <a href="http://heycam.github.io/webidl/#idl-USVString">USVString</a> <var>clientURL</var> = "");
  [NewObject] <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;sequence&lt;<a href="#service-worker-registration-interface">ServiceWorkerRegistration</a>&gt;&gt; <a href="#service-worker-container-getregistrations-method">getRegistrations</a>();


  // events
  attribute <a href="https://html.spec.whatwg.org/multipage/webappapis.html#eventhandler">EventHandler</a> <a href="#service-worker-container-oncontrollerchange-attribute">oncontrollerchange</a>;
  attribute <a href="https://html.spec.whatwg.org/multipage/webappapis.html#eventhandler">EventHandler</a> <a href="#service-worker-container-onerror-attribute">onerror</a>;
  attribute <a href="https://html.spec.whatwg.org/multipage/webappapis.html#eventhandler">EventHandler</a> <a href="#service-worker-container-onmessage-attribute">onmessage</a>; // event.source of message events is ServiceWorker object
};

dictionary <dfn id="registration-option-list-dictionary" title="RegistrationOptions">RegistrationOptions</dfn> {
  <a href="http://heycam.github.io/webidl/#idl-USVString">USVString</a> scope;
};
</code></pre>

  <p id="service-worker-container.1">A <code><a href="#service-worker-container-interface" title="ServiceWorkerContainer">ServiceWorkerContainer</a></code> provides capabilities to register, unregister, and update the <a href="#dfn-service-worker-registration">service worker registrations</a>, and provides access to the state of the <a href="#dfn-service-worker-registration">service worker registrations</a> and their associated <a href="#dfn-service-worker">service workers</a>.</p>
  <p id="service-worker-container.2">A <code><a href="#service-worker-container-interface" title="ServiceWorkerContainer">ServiceWorkerContainer</a></code> has an associated <dfn id="dfn-service-worker-container-interface-client">service worker client</dfn>, which is a <a href="#dfn-service-worker-client">service worker client</a> whose <a href="https://html.spec.whatwg.org/multipage/webappapis.html#global-object">global object</a> is associated with the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#navigator">Navigator</a> object or the <a href="https://html.spec.whatwg.org/multipage/workers.html#workernavigator">WorkerNavigator</a> object that the <code><a href="#service-worker-container-interface">ServiceWorkerContainer</a></code> is retrieved from.</p>

  <p id="service-worker-container.3">A <code><a href="#service-worker-container-interface" title="ServiceWorkerContainer">ServiceWorkerContainer</a></code> object has an associated <dfn id="dfn-ready-promise">ready promise</dfn> (a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a>). It is initially set to null.</p>

  <section title="navigator-service-worker-controller"><header><span class="section-number">3.4.1</span> <h4 id="navigator-service-worker-controller" data-bookmark-label="3.4.1 controller"><code>controller</code></h4><span class="anchor"><a style="text-decoration: none;" href="#navigator-service-worker-controller">¶</a></span></header>


    <p id="navigator-service-worker-controller.1"><dfn id="service-worker-container-controller-attribute"><code>controller</code></dfn> attribute <em class="rfc2119" title="MUST">must</em> return a <code><a href="#service-worker-interface">ServiceWorker</a></code> object that represents the <a href="https://dom.spec.whatwg.org/#context-object">context object</a>'s <a href="#dfn-service-worker-container-interface-client">service worker client</a>'s <a href="#dfn-service-worker-client-active-worker">active worker</a>.</p>
    <p class="note" id="navigator-service-worker-controller.2"><code><a href="#service-worker-container-controller-attribute">navigator.serviceWorker.controller</a></code> returns <code>null</code> if the request is a force refresh (shift+refresh).</p>
  </section>
  <section title="navigator-service-worker-ready"><header><span class="section-number">3.4.2</span> <h4 id="navigator-service-worker-ready" data-bookmark-label="3.4.2 ready"><code>ready</code></h4><span class="anchor"><a style="text-decoration: none;" href="#navigator-service-worker-ready">¶</a></span></header>


    <p id="navigator-service-worker-ready.1"><dfn id="service-worker-container-ready-attribute"><code>ready</code></dfn> attribute <em class="rfc2119" title="MUST">must</em> return the result of running these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>
    <div class="algorithm">
    <ol>
      <li>If the <a href="https://dom.spec.whatwg.org/#context-object">context object</a>'s <a href="#dfn-ready-promise">ready promise</a> is null, then:
        <ol>
          <li>Set the <a href="https://dom.spec.whatwg.org/#context-object">context object</a>'s <a href="#dfn-ready-promise">ready promise</a> to a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a>.</li>
        </ol>
      </li>
      <li>If the <a href="https://dom.spec.whatwg.org/#context-object">context object</a>'s <a href="#dfn-ready-promise">ready promise</a> is settled, then:
        <ol>
          <li>Return the <a href="https://dom.spec.whatwg.org/#context-object">context object</a>'s <a href="#dfn-ready-promise">ready promise</a>.</li>
        </ol>
      </li>
      <li>Let <var>registration</var> be null.</li>
      <li>Let <var>clientURL</var> be the <a href="https://dom.spec.whatwg.org/#context-object">context object</a>'s <a href="#dfn-service-worker-container-interface-client">service worker client</a>'s <a href="https://www.w3.org/Bugs/Public/show_bug.cgi?id=27146">creation url</a>.</li>
      <li>Run the following substeps in parallel:
        <ol>
          <li><em>CheckRegistration</em>: If the result of running <a href="#scope-match-algorithm">Match Service Worker Registration</a> algorithm, or its <a href="#dfn-processing-equivalence">equivalent</a>, with <var>clientURL</var> as its argument is not null, then:
            <ol>
              <li>Set <var>registration</var> to the result value.</li>
            </ol>
          </li>
          <li>Else:
            <ol>
              <li>Wait until <a href="#dfn-scope-to-registration-map">scope to registration map</a> has a new entry.</li>
              <li>Jump to the step labeled <em>CheckRegistration</em>.</li>
            </ol>
          </li>
          <li>If <var>registration</var>'s <a href="#dfn-active-worker">active worker</a> is null, then:
            <ol>
              <li>Wait until <var>registration</var>'s <a href="#dfn-active-worker">active worker</a> changes.</li>
            </ol>
            <p class="note">Implementers should consider this condition is met when the corresponding registration request gets to the step 10 of <a href="#activation-algorithm">Activate</a> algorithm.</p>
          </li>
          <li>Resolve <a href="https://dom.spec.whatwg.org/#context-object">context object</a>'s <a href="#dfn-ready-promise">ready promise</a> with a <code><a href="#service-worker-registration-interface">ServiceWorkerRegistration</a></code> object, setting its <a href="#dfn-service-worker-registration-interface-client">service worker client</a> to <a href="#dfn-service-worker-container-interface-client">service worker client</a>, which represents <var>registration</var>.</li>
        </ol>
      </li>
      <li>Return <a href="https://dom.spec.whatwg.org/#context-object">context object</a>'s <a href="#dfn-ready-promise">ready promise</a>.</li>
    </ol>
    </div>
    <p class="note" id="navigator-service-worker-ready.2">The <code><a href="#service-worker-container-ready-attribute">ready</a></code> attribute is designed in a way that the returned <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> will never reject. Instead, it waits until the <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> resolves with a <a href="#dfn-service-worker-registration">service worker registration</a> that has an <a href="#dfn-active-worker">active worker</a>.</p>
  </section>

  <section title="navigator-service-worker-register"><header><span class="section-number">3.4.3</span> <h4 id="navigator-service-worker-register" data-bookmark-label="3.4.3 register(scriptURL, options)"><code>register(<var>scriptURL</var>, <var>options</var>)</code></h4><span class="anchor"><a style="text-decoration: none;" href="#navigator-service-worker-register">¶</a></span></header>


    <p class="note" id="navigator-service-worker-register.1">The <code><a href="#service-worker-container-register-method">register(<var>scriptURL</var>, <var>options</var>)</a></code> method creates or updates a <a href="#dfn-service-worker-registration">service worker registration</a> for the given <a href="#dfn-scope-url">scope url</a>. If successful, a <a href="#dfn-service-worker-registration">service worker registration</a> ties the provided <var>script url</var> to a <a href="#dfn-scope-url">scope url</a>, which is subsequently used for <a href="#on-fetch-request-algorithm">navigation matching</a>.</p>

    <p id="navigator-service-worker-register.2"><dfn id="service-worker-container-register-method"><code>register(<var>scriptURL</var>, <var>options</var>)</code></dfn> method <em class="rfc2119" title="MUST">must</em> return the result of running these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>
    <div class="algorithm">
    <ol>
      <li>Let <var>scriptURL</var> be the result of <a href="https://url.spec.whatwg.org/#concept-url-parser">parsing</a> <var>scriptURL</var> with <a href="https://html.spec.whatwg.org/multipage/webappapis.html#entry-settings-object">entry settings object</a>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#api-base-url">API base URL</a>.</li>
      <li>If <var>scriptURL</var> is failure, return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with a <code>TypeError</code>.</li>
      <li>Let <var>scopeURL</var> be null.</li>
      <li>If the optional argument <var>options</var> is omitted or <var>options</var>.<var>scope</var> is not present, set <var>scopeURL</var> to the result of <a href="https://url.spec.whatwg.org/#concept-url-parser">parsing</a> a string "<code>./</code>" with <var>scriptURL</var>.
        <p class="note">The scope url for the registration is set to the location of the service worker script by default.</p>
      </li>
      <li>Else, set <var>scopeURL</var> to the result of <a href="https://url.spec.whatwg.org/#concept-url-parser">parsing</a> <var>options</var>.<var>scope</var> with <a href="https://html.spec.whatwg.org/multipage/webappapis.html#entry-settings-object">entry settings object</a>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#api-base-url">API base URL</a>.</li>
      <li>If <var>scopeURL</var> is failure, return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with a <code>TypeError</code>.</li>
      <li>Return the result of running the <a href="#register-algorithm">Register</a> algorithm, or its <a href="#dfn-processing-equivalence">equivalent</a>, passing the <a href="#dfn-service-worker-container-interface-client">service worker client</a> <var>client</var>, <var>scriptURL</var>, <var>scopeURL</var> as the arguments.</li>
    </ol>
    </div>
  </section>

  <section title="navigator-service-worker-getRegistration"><header><span class="section-number">3.4.4</span> <h4 id="navigator-service-worker-getRegistration" data-bookmark-label="3.4.4 getRegistration(clientURL)"><code>getRegistration(<var>clientURL</var>)</code></h4><span class="anchor"><a style="text-decoration: none;" href="#navigator-service-worker-getRegistration">¶</a></span></header>


    <p id="navigator-service-worker-getRegistration.1"><dfn id="service-worker-container-getregistration-method"><code>getRegistration(<var>clientURL</var>)</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>

    <div class="algorithm">
    <ol>
      <li>Let <var>clientURL</var> be the result of <a href="https://url.spec.whatwg.org/#concept-url-parser">parsing</a> <var>clientURL</var> with <a href="https://html.spec.whatwg.org/multipage/webappapis.html#entry-settings-object">entry settings object</a>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#api-base-url">API base URL</a>.</li>
      <li>If <var>clientURL</var> is failure, return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with a <code>TypeError</code>.</li>
      <li>If the <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a> of <var>clientURL</var> is not the <a href="https://dom.spec.whatwg.org/#context-object">context object</a>'s <a href="#dfn-service-worker-container-interface-client">service worker client</a>'s <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a>, return a <var>promise</var> with a "<code><a href="http://heycam.github.io/webidl/#securityerror">SecurityError</a></code>" exception.</li>
      <li>Let <var>promise</var> be a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a>.</li>
      <li>Run the following substeps in parallel:
        <ol>
          <li>Let <var>registration</var> be the result of running <a href="#scope-match-algorithm">Match Service Worker Registration</a> algorithm, or its equivalent, with <var>clientURL</var> as its argument.</li>
          <li>If <var>registration</var> is not null, then:
            <ol>
              <li>Resolve <var>promise</var> with a <code><a href="#service-worker-registration-interface">ServiceWorkerRegistration</a></code> object, setting its <a href="#dfn-service-worker-registration-interface-client">service worker client</a> to <a href="#dfn-service-worker-container-interface-client">service worker client</a>, which represents <var>registration</var>.</li>
            </ol>
          </li>
          <li>Else:
            <ol>
              <li>Resolve <var>promise</var> with <code>undefined</code>.</li>
            </ol>
          </li>
        </ol>
      </li>
      <li>Return <var>promise</var>.</li>
    </ol>
    </div>
  </section>

  <section title="navigator-service-worker-getRegistrations"><header><span class="section-number">3.4.5</span> <h4 id="navigator-service-worker-getRegistrations" data-bookmark-label="3.4.5 getRegistrations()"><code>getRegistrations()</code></h4><span class="anchor"><a style="text-decoration: none;" href="#navigator-service-worker-getRegistrations">¶</a></span></header>


    <p id="navigator-service-worker-getRegistrations.1"><dfn id="service-worker-container-getregistrations-method"><code>getRegistrations()</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>

    <div class="algorithm">
    <ol>
      <li>Let <var>promise</var> be a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a>.</li>
      <li>Run the following substeps in parallel:
        <ol>
          <li>Let <var>array</var> be an empty array.</li>
          <li>For each <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-list-and-record-specification-type">Record</a> {[[key]], [[value]]} <var>entry</var> of its <a href="#dfn-scope-to-registration-map">scope to registration map</a>:
            <ol>
              <li>If the <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a> of the result of <a href="https://url.spec.whatwg.org/#concept-url-parser">parsing</a> <var>entry</var>.[[key]] is its <a href="#dfn-service-worker-container-interface-client">service worker client</a>'s <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a>, then:
                <ol>
                  <li>Add a <code><a href="#service-worker-registration-interface">ServiceWorkerRegistration</a></code> object, setting its <a href="#dfn-service-worker-registration-interface-client">service worker client</a> to <a href="#dfn-service-worker-container-interface-client">service worker client</a>, associated with <var>entry</var>.[[value]] to the <var>array</var>.</li>
                </ol>
              </li>
            </ol>
          </li>
          <li>Resolve <var>promise</var> with <var>array</var>.</li>
        </ol>
      </li>
      <li>Return <var>promise</var>.</li>
    </ol>
    </div>
  </section>

  <section title="service-worker-container-event-handlers"><header><span class="section-number">3.4.6</span> <h4 id="service-worker-container-event-handlers" data-bookmark-label="3.4.6 Event handlers">Event handlers</h4><span class="anchor"><a style="text-decoration: none;" href="#service-worker-container-event-handlers">¶</a></span></header>


      <p id="service-worker-container-event-handlers.1">The following are the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-handlers">event handlers</a> (and its corresponding <a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-handler-event-type">event handler event types</a>) that <em class="rfc2119" title="MUST">must</em> be supported, as <a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-handler-idl-attributes">event handler IDL attributes</a>, by all objects implementing the <a href="#service-worker-container-interface">ServiceWorkerContainer</a> interface:</p>

      <table>
        <thead>
          <tr>
            <th><a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-handlers">event handler</a></th>
            <th><a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-handler-event-type">event handler event type</a></th>
          </tr>
        </thead>
        <tbody>
          <tr>
            <td><dfn id="service-worker-container-oncontrollerchange-attribute"><code>oncontrollerchange</code></dfn></td>
            <td><code><a href="#service-worker-container-controllerchange-event">controllerchange</a></code></td>
          </tr>
          <tr>
            <td><dfn id="service-worker-container-onerror-attribute"><code>onerror</code></dfn></td>
            <td><code><a href="#service-worker-container-error-event">error</a></code></td>
          </tr>
          <tr>
            <td><dfn id="service-worker-container-onmessage-attribute"><code>onmessage</code></dfn></td>
            <td><code><a href="#service-worker-container-message-event">message</a></code></td>
          </tr>
        </tbody>
      </table>
    </section>
  </section>

  <section title="serviceworkermessage-event-section"><header><span class="section-number">3.5</span> <h3 id="serviceworkermessage-event-section" data-bookmark-label="3.5 ServiceWorkerMessageEvent"><code>ServiceWorkerMessageEvent</code></h3><span class="anchor"><a style="text-decoration: none;" href="#serviceworkermessage-event-section">¶</a></span></header>


<pre><code>[Constructor(DOMString <var>type</var>, optional <a href="#serviceworkermessage-event-init-dictionary">ServiceWorkerMessageEventInit</a> <var>eventInitDict</var>), Exposed=(Window,Worker)]
interface <dfn id="serviceworkermessage-event-interface" title="ServiceWorkerMessageEvent">ServiceWorkerMessageEvent</dfn> : <a href="https://html.spec.whatwg.org/multipage/infrastructure.html#event">Event</a> {
  readonly attribute any <a href="#serviceworkermessage-event-data-attribute">data</a>;
  readonly attribute DOMString <a href="#serviceworkermessage-event-origin-attribute">origin</a>;
  readonly attribute DOMString <a href="#serviceworkermessage-event-lasteventid-attribute">lastEventId</a>;
  [SameObject] readonly attribute (<a href="#service-worker-interface">ServiceWorker</a> or <a href="https://html.spec.whatwg.org/multipage/comms.html#messageport">MessagePort</a>)? <a href="#serviceworkermessage-event-source-attribute">source</a>;
  [SameObject] readonly attribute <a href="https://html.spec.whatwg.org/multipage/comms.html#messageport">MessagePort</a>[]? <a href="#serviceworkermessage-event-ports-attribute">ports</a>;
};

dictionary <dfn id="serviceworkermessage-event-init-dictionary" title="ServiceWorkerMessageEventInit">ServiceWorkerMessageEventInit</dfn> : <a href="https://dom.spec.whatwg.org/#dictdef-eventinit">EventInit</a> {
  any data;
  DOMString origin;
  DOMString lastEventId;
  (<a href="#service-worker-interface">ServiceWorker</a> or <a href="https://html.spec.whatwg.org/multipage/comms.html#messageport">MessagePort</a>)? source;
  sequence&lt;<a href="https://html.spec.whatwg.org/multipage/comms.html#messageport">MessagePort</a>&gt; ports;
};
</code></pre>
    <p id="serviceworkermessage-event-section.1"><a href="#dfn-service-worker">Service workers</a> define the <a href="#service-worker-container-message-event">message</a> event that extends the <a href="https://html.spec.whatwg.org/multipage/indices.html#event-message">message</a> event defined in <a href="https://html.spec.whatwg.org/">HTML</a> to allow setting a <code><a href="#service-worker-interface">ServiceWorker</a></code> object as the source of the message. For the <a href="#service-worker-container-message-event">message</a> event, <a href="#dfn-service-worker">service workers</a> use the <code><a href="#serviceworkermessage-event-interface">ServiceWorkerMessageEvent</a></code> interface.</p>

    <section title="serviceworkermessage-event-data"><header><span class="section-number">3.5.1</span> <h4 id="serviceworkermessage-event-data" data-bookmark-label="3.5.1 event.data"><code>event.data</code></h4><span class="anchor"><a style="text-decoration: none;" href="#serviceworkermessage-event-data">¶</a></span></header>

      <p id="serviceworkermessage-event-data.1">The <dfn id="serviceworkermessage-event-data-attribute">data</dfn> attribute <em class="rfc2119" title="MUST">must</em> return the value it was initialized to. When the object is created, this attribute <em class="rfc2119" title="MUST">must</em> be initialized to null. It represents the message being sent.</p>
    </section>

    <section title="serviceworkermessage-event-origin"><header><span class="section-number">3.5.2</span> <h4 id="serviceworkermessage-event-origin" data-bookmark-label="3.5.2 event.origin"><code>event.origin</code></h4><span class="anchor"><a style="text-decoration: none;" href="#serviceworkermessage-event-origin">¶</a></span></header>

      <p id="serviceworkermessage-event-origin.1">The <dfn id="serviceworkermessage-event-origin-attribute">origin</dfn> attribute <em class="rfc2119" title="MUST">must</em> return the value it was initialized to. When the object is created, this attribute <em class="rfc2119" title="MUST">must</em> be initialized to the empty string. It represents the <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a> of the <a href="#dfn-service-worker">service worker</a>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#environment-settings-object">environment settings object</a> from which the message is sent.</p>
    </section>

    <section title="serviceworkermessage-event-lasteventid"><header><span class="section-number">3.5.3</span> <h4 id="serviceworkermessage-event-lasteventid" data-bookmark-label="3.5.3 event.lastEventId"><code>event.lastEventId</code></h4><span class="anchor"><a style="text-decoration: none;" href="#serviceworkermessage-event-lasteventid">¶</a></span></header>

      <p id="serviceworkermessage-event-lasteventid.1">The <dfn id="serviceworkermessage-event-lasteventid-attribute">lastEventId</dfn> attribute <em class="rfc2119" title="MUST">must</em> return the value it was initialized to. When the object is created, this attribute <em class="rfc2119" title="MUST">must</em> be initialized to the empty string.</p>
    </section>

    <section title="serviceworkermessage-event-source"><header><span class="section-number">3.5.4</span> <h4 id="serviceworkermessage-event-source" data-bookmark-label="3.5.4 event.source"><code>event.source</code></h4><span class="anchor"><a style="text-decoration: none;" href="#serviceworkermessage-event-source">¶</a></span></header>

      <p id="serviceworkermessage-event-source.1">The <dfn id="serviceworkermessage-event-source-attribute">source</dfn> attribute <em class="rfc2119" title="MUST">must</em> return the value it was initialized to. When the object is created, this attribute <em class="rfc2119" title="MUST">must</em> be initialized to null. It represents the <code><a href="#client-interface">ServiceWorker</a></code> object whose associated <a href="#dfn-service-worker">service worker</a> the message is sent from.</p>

      <p class="note" id="serviceworkermessage-event-source.2">When <a href="https://github.com/mkruisselbrink/navigator-connect/">navigator.connect() API</a> extends the service worker communication model, this attribute may also represent <a href="https://mkruisselbrink.github.io/navigator-connect/#idl-def-ServicePort">ServicePort</a> object from which the message is sent.</p>
    </section>

    <section title="serviceworkermessage-event-ports"><header><span class="section-number">3.5.5</span> <h4 id="serviceworkermessage-event-ports" data-bookmark-label="3.5.5 event.ports"><code>event.ports</code></h4><span class="anchor"><a style="text-decoration: none;" href="#serviceworkermessage-event-ports">¶</a></span></header>

      <p id="serviceworkermessage-event-ports.1">The <dfn id="serviceworkermessage-event-ports-attribute">ports</dfn> attribute <em class="rfc2119" title="MUST">must</em> return the value it was initialized to. When the object is created, this attribute <em class="rfc2119" title="MUST">must</em> be initialized to null. It represents the <a href="https://html.spec.whatwg.org/multipage/comms.html#messageport">MessagePort</a> array being sent, if any.</p>
    </section>
  </section>

  <section title="document-context-events"><header><span class="section-number">3.6</span> <h3 id="document-context-events" data-bookmark-label="3.6 Events">Events</h3><span class="anchor"><a style="text-decoration: none;" href="#document-context-events">¶</a></span></header>


    <p id="document-context-events.1">The following event is dispatched on <code><a href="#service-worker-interface">ServiceWorker</a></code> object:</p>

    <table>
      <thead>
        <tr>
          <th>Event name</th>
          <th>Interface</th>
          <th>Dispatched when…</th>
        </tr>
      </thead>
      <tbody>
        <tr>
          <td><dfn id="service-worker-statechange-event"><code>statechange</code></dfn></td>
          <td><code><a href="https://dom.spec.whatwg.org/#event">Event</a></code></td>
          <td>The <code><a href="#service-worker-state-attribute">state</a></code> attribute of the <code><a href="#service-worker-interface">ServiceWorker</a></code> object is changed.</td>
        </tr>
      </tbody>
    </table>

    <p id="document-context-events.2">The following event is dispatched on <code><a href="#service-worker-registration-interface">ServiceWorkerRegistration</a></code> object:</p>

    <table>
      <thead>
        <tr>
          <th>Event name</th>
          <th>Interface</th>
          <th>Dispatched when…</th>
        </tr>
      </thead>
      <tbody>
        <tr>
          <td><dfn id="service-worker-registration-updatefound-event"><code>updatefound</code></dfn></td>
          <td><code><a href="https://dom.spec.whatwg.org/#event">Event</a></code></td>
          <td>The <a href="#dfn-service-worker-registration-interface-service-worker-registration">service worker registration</a>'s <a href="#dfn-installing-worker">installing worker</a> changes. (See step 8 of the <a href="#installation-algorithm">Install</a> algorithm).</td>
        </tr>
      </tbody>
    </table>

    <p id="document-context-events.3">The following events are dispatched on <code><a href="#service-worker-container-interface">ServiceWorkerContainer</a></code> object:</p>

    <table>
      <thead>
        <tr>
          <th>Event name</th>
          <th>Interface</th>
          <th>Dispatched when…</th>
        </tr>
      </thead>
      <tbody>
        <tr>
          <td><dfn id="service-worker-container-controllerchange-event"><code>controllerchange</code></dfn></td>
          <td><code><a href="https://dom.spec.whatwg.org/#event">Event</a></code></td>
          <td>The <a href="#dfn-service-worker-container-interface-client">service worker client</a>'s <a href="#dfn-service-worker-client-active-worker">active worker</a> changes. (See step 12.2 of the <a href="#activation-algorithm">Activate</a> algorithm. The <a href="#dfn-skip-waiting-flag">skip waiting flag</a> of a <a href="#dfn-service-worker">service worker</a> causes <a href="#activation-algorithm">activation</a> of the <a href="#dfn-service-worker-registration">service worker registration</a> to occur while <a href="#dfn-service-worker-client">service worker clients</a> are <a href="#dfn-use">using</a> the <a href="#dfn-service-worker-registration">service worker registration</a>, <code><a href="#service-worker-container-controller-attribute">navigator.serviceWorker.controller</a></code> immediately reflects the <a href="#dfn-active-worker">active worker</a> as the <a href="#dfn-service-worker">service worker</a> that <a href="#dfn-control">controls</a> the <a href="#dfn-service-worker-client">service worker client</a>.)</td>
        </tr>
        <tr>
          <td><dfn id="service-worker-container-message-event"><code>message</code></dfn></td>
          <td><code><a href="#serviceworkermessage-event-interface">ServiceWorkerMessageEvent</a></code></td>
          <td>When it receives a message.</td>
        </tr>
        <tr>
          <td><dfn id="service-worker-container-error-event"><code>error</code></dfn></td>
          <td><code><a href="https://html.spec.whatwg.org/multipage/webappapis.html#errorevent">ErrorEvent</a></code></td>
          <td>Any error occurred from the associated <a href="#dfn-service-worker">service workers</a>.</td>
        </tr>
      </tbody>
    </table>
  </section>
</section>

<section title="execution-context"><header><span class="section-number">4</span> <h2 id="execution-context" data-bookmark-label="4 Execution Context">Execution Context</h2><span class="anchor"><a style="text-decoration: none;" href="#execution-context">¶</a></span></header>


  <p id="execution-context.1">Example: Serving Cached Resources</p>

<pre><code>// caching.js
this.addEventListener("install", function(e) {
  e.waitUntil(
    // Open a cache of resources.
    caches.open("shell-v1").then(function(cache) {
      // Begins the process of fetching them.
      // The coast is only clear when all the resources are ready.
      return cache.addAll([
        "/app.html",
        "/assets/v1/base.css",
        "/assets/v1/app.js",
        "/assets/v1/logo.png",
        "/assets/v1/intro_video.webm"
      ]);
    })
  );
});

this.addEventListener("fetch", function(e) {
  // No "fetch" events are dispatched to the service worker until it
  // successfully installs and activates.

  // All operations on caches are async, including matching URLs, so we use
  // promises heavily. e.respondWith() even takes promises to enable this:
  e.respondWith(
    caches.match(e.request).then(function(response) {
      return response || fetch(e.request);
    }).catch(function() {
      return caches.match("/fallback.html");
    })
  );
});</code></pre>

  <section title="service-worker-global-scope"><header><span class="section-number">4.1</span> <h3 id="service-worker-global-scope" data-bookmark-label="4.1 ServiceWorkerGlobalScope"><code>ServiceWorkerGlobalScope</code></h3><span class="anchor"><a style="text-decoration: none;" href="#service-worker-global-scope">¶</a></span></header>


<pre><code>[<a href="http://heycam.github.io/webidl/#Global">Global</a>=(Worker,ServiceWorker), Exposed=ServiceWorker]
interface <dfn id="service-worker-global-scope-interface" title="ServiceWorkerGlobalScope">ServiceWorkerGlobalScope</dfn> : <a href="http://www.w3.org/TR/workers/#workerglobalscope">WorkerGlobalScope</a> {
  // A container for a list of Client objects that correspond to
  // browsing contexts (or shared workers) that are on the origin of this SW
  [SameObject] readonly attribute <a href="#clients-interface">Clients</a> <a href="#service-worker-global-scope-clients-attribute">clients</a>;
  [SameObject] readonly attribute <a href="#service-worker-registration-interface">ServiceWorkerRegistration</a> <a href="#service-worker-global-scope-registration">registration</a>;

  [NewObject] <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;void&gt; <a href="#service-worker-global-scope-skipwaiting-method">skipWaiting</a>();

  attribute <a href="https://html.spec.whatwg.org/multipage/webappapis.html#eventhandler">EventHandler</a> <a href="#service-worker-global-scope-oninstall-attribute">oninstall</a>;
  attribute <a href="https://html.spec.whatwg.org/multipage/webappapis.html#eventhandler">EventHandler</a> <a href="#service-worker-global-scope-onactivate-attribute">onactivate</a>;
  attribute <a href="https://html.spec.whatwg.org/multipage/webappapis.html#eventhandler">EventHandler</a> <a href="#service-worker-global-scope-onfetch-attribute">onfetch</a>;

  // event
  attribute <a href="https://html.spec.whatwg.org/multipage/webappapis.html#eventhandler">EventHandler</a> <a href="#service-worker-global-scope-onmessage-attribute">onmessage</a>; // event.source of the message events is Client object

  // close() method inherited from WorkerGlobalScope <a href="#service-worker-global-scope-close-method"><em class="rfc2119" title="SHOULD NOT">should not</em> be accessible</a>.
};
</code></pre>

    <p id="service-worker-global-scope.1">A <code><a href="#service-worker-global-scope-interface">ServiceWorkerGlobalScope</a></code> object represents the global execution context of a <a href="#dfn-service-worker">service worker</a>. A <code><a href="#service-worker-global-scope-interface">ServiceWorkerGlobalScope</a></code> object has an associated <dfn id="dfn-service-worker-global-scope-service-worker">service worker</dfn> (a <a href="#dfn-service-worker">service worker</a>).</p>
    <p class="note" id="service-worker-global-scope.2"><code><a href="#service-worker-global-scope-interface">ServiceWorkerGlobalScope</a></code> object provides generic, event-driven, time-limited script execution contexts that run at an origin. Once successfully <a href="#navigator-service-worker-register">registered</a>, a <a href="#dfn-service-worker">service worker</a> is started, kept alive and killed by their relationship to events, not <a href="#dfn-service-worker-client">service worker clients</a>. Any type of synchronous requests must not be initiated inside of a <a href="#dfn-service-worker">service worker</a>.</p>

    <p id="service-worker-global-scope-close-method" class="note"><a id="service-worker-global-scope.3"></a>The <code><a href="http://www.w3.org/TR/workers/#dom-workerglobalscope-close">close()</a></code> method inherited from <code><a href="http://www.w3.org/TR/workers/#workerglobalscope">WorkerGlobalScope</a></code>, when called on the <a href="https://dom.spec.whatwg.org/#context-object">context object</a>, should <a href="http://heycam.github.io/webidl/#dfn-throw">throw</a> an "<code><a href="http://heycam.github.io/webidl/#invalidaccesserror">InvalidAccessError</a></code>" exception.</p>

    <section title="service-worker-global-scope-clients"><header><span class="section-number">4.1.1</span> <h4 id="service-worker-global-scope-clients" data-bookmark-label="4.1.1 clients"><code>clients</code></h4><span class="anchor"><a style="text-decoration: none;" href="#service-worker-global-scope-clients">¶</a></span></header>


      <p id="service-worker-global-scope-clients.1"><dfn id="service-worker-global-scope-clients-attribute"><code>clients</code></dfn> attribute <em class="rfc2119" title="MUST">must</em> return the <code><a href="#clients-interface">Clients</a></code> object.</p>
    </section>
    <section title="service-worker-global-scope-registration"><header><span class="section-number">4.1.2</span> <h4 id="service-worker-global-scope-registration" data-bookmark-label="4.1.2 registration"><code>registration</code></h4><span class="anchor"><a style="text-decoration: none;" href="#service-worker-global-scope-registration">¶</a></span></header>


      The <dfn id="service-worker-global-scope-scope-attribute"><code>registration</code></dfn> attribute <em class="rfc2119" title="MUST">must</em> return the <code><a href="#service-worker-registration-interface">ServiceWorkerRegistration</a></code> object that represents the <a href="#dfn-service-worker-global-scope-service-worker">service worker</a>'s <a href="#dfn-containing-service-worker-registration">containing service worker registration</a>.<p id="service-worker-global-scope-registration.1"></p>
    </section>

    <section title="service-worker-global-scope-skipwaiting"><header><span class="section-number">4.1.3</span> <h4 id="service-worker-global-scope-skipwaiting" data-bookmark-label="4.1.3 skipWaiting()"><code>skipWaiting()</code></h4><span class="anchor"><a style="text-decoration: none;" href="#service-worker-global-scope-skipwaiting">¶</a></span></header>


      <p class="note" id="service-worker-global-scope-skipwaiting.1">The <code><a href="#service-worker-global-scope-skipwaiting-method">skipWaiting()</a></code> method allows this <a href="#dfn-service-worker">service worker</a> to progress from the <a href="#dfn-containing-service-worker-registration">registration</a>'s <a href="#dfn-waiting-worker">waiting</a> position to <a href="#dfn-active-worker">active</a> even while <a href="#service-worker-client-concept">service worker clients</a> are <a href="#dfn-use">using</a> the <a href="#dfn-containing-service-worker-registration">registration</a>.</p>

      <p id="service-worker-global-scope-skipwaiting.2"><dfn id="service-worker-global-scope-skipwaiting-method"><code>skipWaiting()</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>

      <div class="algorithm">
      <ol>
        <li>Let <var>promise</var> be a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a>.</li>
        <li>Run the following substeps in parallel:
          <ol>
            <li>Set <a href="#dfn-service-worker">service worker</a>'s <a href="#dfn-skip-waiting-flag">skip waiting flag</a></li>
            <li>If <a href="#dfn-service-worker">service worker</a>'s <a href="#dfn-state">state</a> is <em>installed</em>, then:
              <ol>
                <li>Run <a href="#activation-algorithm">Activate</a> algorithm, or its <a href="#dfn-processing-equivalence">equivalent</a>, passing <a href="#dfn-service-worker">service worker</a>'s <a href="#dfn-containing-service-worker-registration">registration</a> as the argument.</li>
              </ol>
            </li>
            <li>Resolve <var>promise</var> with undefined.</li>
          </ol>
        </li>
        <li>Return <var>promise</var>.</li>
      </ol>
      </div>
    </section>

    <section title="service-worker-global-scope-event-handlers"><header><span class="section-number">4.1.4</span> <h4 id="service-worker-global-scope-event-handlers" data-bookmark-label="4.1.4 Event handlers">Event handlers</h4><span class="anchor"><a style="text-decoration: none;" href="#service-worker-global-scope-event-handlers">¶</a></span></header>


      <p id="service-worker-global-scope-event-handlers.1">The following are the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-handlers">event handlers</a> (and its corresponding <a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-handler-event-type">event handler event types</a>) that <em class="rfc2119" title="MUST">must</em> be supported, as <a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-handler-idl-attributes">event handler IDL attributes</a>, by all objects implementing the <a href="#service-worker-global-scope-interface">ServiceWorkerGlobalScope</a> interface:</p>

      <table>
        <thead>
          <tr>
            <th><a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-handlers">event handler</a></th>
            <th><a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-handler-event-type">event handler event type</a></th>
          </tr>
        </thead>
        <tbody>
          <tr>
            <td><dfn id="service-worker-global-scope-oninstall-attribute"><code>oninstall</code></dfn></td>
            <td><code><a href="#service-worker-global-scope-install-event">install</a></code></td>
          </tr>
          <tr>
            <td><dfn id="service-worker-global-scope-onactivate-attribute"><code>onactivate</code></dfn></td>
            <td><code><a href="#service-worker-global-scope-activate-event">activate</a></code></td>
          </tr>
          <tr>
            <td><dfn id="service-worker-global-scope-onfetch-attribute"><code>onfetch</code></dfn></td>
            <td><code><a href="#service-worker-global-scope-fetch-event">fetch</a></code></td>
          </tr>
          <tr>
            <td><dfn id="service-worker-global-scope-onmessage-attribute"><code>onmessage</code></dfn></td>
            <td><code><a href="#service-worker-global-scope-message-event">message</a></code></td>
          </tr>
        </tbody>
      </table>
    </section>
  </section>
  <section title="client"><header><span class="section-number">4.2</span> <h3 id="client" data-bookmark-label="4.2 Client"><code>Client</code></h3><span class="anchor"><a style="text-decoration: none;" href="#client">¶</a></span></header>


<pre><code>[Exposed=ServiceWorker]
interface <dfn id="client-interface" title="Client">Client</dfn> {
  readonly attribute <a href="http://heycam.github.io/webidl/#idl-USVString">USVString</a> url;
  readonly attribute <a href="#contextframetype-enum">FrameType</a> <a href="#client-frametype-attribute">frameType</a>;
  readonly attribute DOMString <a href="#client-id-attribute">id</a>;
  void <a href="#client-postmessage-method">postMessage</a>(any <var>message</var>, optional sequence&lt;<a href="https://html.spec.whatwg.org/multipage/infrastructure.html#transferable">Transferable</a>&gt; <var>transfer</var>);
};

[Exposed=ServiceWorker]
interface <dfn id="window-client-interface" title="WindowClient">WindowClient</dfn> : <a href="#client-interface">Client</a> {
  readonly attribute <a href="http://www.w3.org/TR/page-visibility/#VisibilityState">VisibilityState</a> <a href="#client-visibilitystate-attribute">visibilityState</a>;
  readonly attribute boolean <a href="#client-focused-attribute">focused</a>;
  [NewObject] <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;<a href="#window-client-interface">WindowClient</a>&gt; <a href="#client-focus-method">focus</a>();
  [NewObject] <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;<a href="#window-client-interface">WindowClient</a>&gt; <a href="#client-navigate-method">navigate</a>(<a href="http://heycam.github.io/webidl/#idl-USVString">USVString</a> <var>url</var>);
};

enum <dfn id="contextframetype-enum" title="ContextFrameType">FrameType</dfn> {
  "auxiliary",
  "top-level",
  "nested",
  "none"
};
</code></pre>
    <p id="client.1">A <code><a href="#client-interface">Client</a></code> object has an associated <dfn id="dfn-service-worker-client-client">service worker client</dfn> (a <a href="#dfn-service-worker-client">service worker client</a>).</p>

    <p id="client.2">A <code><a href="#window-client-interface">WindowClient</a></code> object has an associated <dfn id="dfn-service-worker-client-visibilitystate">visibility state</dfn>, which is one of <a href="http://www.w3.org/TR/page-visibility/#dom-document-visibilitystate">visibilityState</a> attribute value.</p>

    <p id="client.3">A <code><a href="#window-client-interface">WindowClient</a></code> object has an associated <dfn id="dfn-service-worker-client-focusstate">focus state</dfn>, which is either true or false. (Initially false).</p>

    <section title="client-url"><header><span class="section-number">4.2.1</span> <h4 id="client-url" data-bookmark-label="4.2.1 url"><code>url</code></h4><span class="anchor"><a style="text-decoration: none;" href="#client-url">¶</a></span></header>


      <p id="client-url.1">The <dfn id="client-url-attribute"><code>url</code></dfn> attribute <em class="rfc2119" title="MUST">must</em> return the <a href="https://dom.spec.whatwg.org/#context-object">context object</a>'s associated <a href="#dfn-service-worker-client-client">service worker client</a>'s <a href="https://url.spec.whatwg.org/#concept-url-serializer">serialized</a> <a href="https://www.w3.org/Bugs/Public/show_bug.cgi?id=27146">creation url</a>.</p>
    </section>

    <section title="client-frametype"><header><span class="section-number">4.2.2</span> <h4 id="client-frametype" data-bookmark-label="4.2.2 frameType"><code>frameType</code></h4><span class="anchor"><a style="text-decoration: none;" href="#client-frametype">¶</a></span></header>


      <p id="client-frametype.1">The <dfn id="client-frametype-attribute"><code>frameType</code></dfn> attribute <em class="rfc2119" title="MUST">must</em> return the value (in <a href="#contextframetype-enum">FrameType</a> enumeration) corresponding to the first matching statement, switching on <a href="#dfn-service-worker-client-client">service worker client</a>'s <a href="#dfn-window-client-frametype">frame type</a>:</p>

      <dl>
        <dt><em>auxiliary</em></dt>
        <dd>"<code>auxiliary</code>"
        <p class="note">The <a href="#dfn-window-client">window client</a>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#global-object">global object</a>'s <a href="https://html.spec.whatwg.org/multipage/browsers.html#browsing-context">browsing context</a> is an <a href="https://html.spec.whatwg.org/multipage/browsers.html#auxiliary-browsing-context">auxiliary browsing context</a>.</p></dd>

        <dt><em>top-level</em></dt>
        <dd>"<code>top-level</code>"
        <p class="note">The <a href="#dfn-window-client">window client</a>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#global-object">global object</a>'s <a href="https://html.spec.whatwg.org/multipage/browsers.html#browsing-context">browsing context</a> is a <a href="https://html.spec.whatwg.org/multipage/browsers.html#top-level-browsing-context">top-level browsing context</a>.</p></dd>

        <dt><em>nested</em></dt>
        <dd>"<code>nested</code>"
        <p class="note">The <a href="#dfn-window-client">window client</a>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#global-object">global object</a>'s <a href="https://html.spec.whatwg.org/multipage/browsers.html#browsing-context">browsing context</a> is a <a href="https://html.spec.whatwg.org/multipage/browsers.html#nested-browsing-context">nested browsing context</a>.</p></dd>

        <dt><em>none</em></dt>
        <dd>"<code>none</code>"</dd>
      </dl>
    </section>

    <section title="client-id"><header><span class="section-number">4.2.3</span> <h4 id="client-id" data-bookmark-label="4.2.3 id"><code>id</code></h4><span class="anchor"><a style="text-decoration: none;" href="#client-id">¶</a></span></header>


      <p id="client-id.1">The <dfn id="client-id-attribute"><code>id</code></dfn> attribute <em class="rfc2119" title="MUST">must</em> return its associated <a href="#dfn-service-worker-client-client">service worker client</a>'s <a href="#dfn-service-worker-client-id">id</a>.</p>
    </section>

    <section title="client-postmessage"><header><span class="section-number">4.2.4</span> <h4 id="client-postmessage" data-bookmark-label="4.2.4 postMessage(message, transfer)"><code>postMessage(<var>message</var>, <var>transfer</var>)</code></h4><span class="anchor"><a style="text-decoration: none;" href="#client-postmessage">¶</a></span></header>


      <p id="client-postmessage.1">The <dfn id="client-postmessage-method"><code>postMessage(<var>message</var>, <var>transfer</var>)</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>
      <div class="algorithm">
      <ol>
        <li>Let <var>newPorts</var> be an empty array.</li>
        <li>Let <var>transferMap</var> be an empty association list of <a href="https://html.spec.whatwg.org/multipage/infrastructure.html#transferable">Transferable</a> objects to placeholder objects.</li>
        <li>If the method was invoked with a second argument <var>transfer</var>, run these substeps:
          <ol>
            <li>If any object is listed in <var>transfer</var> more than once, or any of the <a href="https://html.spec.whatwg.org/multipage/infrastructure.html#transferable">Transferable</a> objects listed in <var>transfer</var> are marked as <a href="https://html.spec.whatwg.org/multipage/infrastructure.html#concept-transferable-neutered">neutered</a>, then <a href="http://heycam.github.io/webidl/#dfn-throw">throw</a> a "<code><a href="http://heycam.github.io/webidl/#datacloneerror">DataCloneError</a></code>" exception and abort these steps.</li>
            <li>For each object <var>x</var> in <var>transfer</var> in turn, add a mapping from <var>x</var> to a new unique placeholder object created for <var>x</var> to <var>transferMap</var>, and if <var>x</var> is a <a href="https://html.spec.whatwg.org/multipage/comms.html#messageport">MessagePort</a> object, also append the placeholder object to <var>newPorts</var>.</li>
          </ol>
        </li>
        <li>Let <var>clonedMessage</var> be a <a href="https://html.spec.whatwg.org/multipage/infrastructure.html#structured-clone">structured clone</a> of <var>message</var> with <var>transferMap</var> as the <var>transferMap</var>. If this <a href="http://heycam.github.io/webidl/#dfn-throw">throws</a> an exception, <a href="http://heycam.github.io/webidl/#dfn-throw">rethrow</a> that exception and abort these steps.</li>
        <li>Let <var>destination</var> be the <code><a href="#service-worker-container-interface">ServiceWorkerContainer</a></code> object whose <a href="#dfn-service-worker-container-interface-client">service worker client</a> is the <a href="https://dom.spec.whatwg.org/#context-object">context object</a>'s <a href="#dfn-service-worker-client-client">service worker client</a>.</li>
        <li>If <var>destination</var> is null, <a href="http://heycam.github.io/webidl/#dfn-throw">throw</a> an "<code><a href="http://heycam.github.io/webidl/#invalidstateerror">InvalidStateError</a></code>" exception.</li>
        <li>If the method was invoked with a second argument <var>transfer</var>, run these substeps:
          <ol>
            <li>Let <var>newOwner</var> be the <var>destination</var>'s <a href="#dfn-service-worker-client-client">service worker client</a>.</li>
            <li>For each object <var>x</var> in <var>transfer</var> in turn, obtain a new object <var>y</var> by <a href="https://html.spec.whatwg.org/multipage/infrastructure.html#transfer-a-transferable-object">transferring</a> the object <var>x</var> to <var>newOwner</var>, and replace the placeholder object that was created for the object <var>x</var> by the new object <var>y</var> wherever the placeholder exists (i.e. in <var>clonedMessage</var> and in <var>newPorts</var>).</li>
          </ol>
        </li>
        <li>Make <var>newPorts</var> into a <a href="https://html.spec.whatwg.org/multipage/infrastructure.html#dfn-read-only-array">read only</a> array.</li>
        <li><a href="https://html.spec.whatwg.org/multipage/webappapis.html#queue-a-task">Queue a task</a> that runs the following steps:
          <ol>
            <li>Create an event <var>e</var> that uses the <code><a href="#serviceworkermessage-event-interface">ServiceWorkerMessageEvent</a></code> interface, with the event type <a href="#service-worker-container-message-event">message</a>, which does not bubble, is not cancelable, and has no default action.</li>
            <li>Let the <a href="https://html.spec.whatwg.org/multipage/comms.html#dom-messageevent-data">data</a> attribute of <var>e</var> be initialized to <var>clonedMessage</var>.</li>
            <li>Let the <a href="https://html.spec.whatwg.org/multipage/comms.html#dom-messageevent-origin">origin</a> attribute of <var>e</var> be initialized to the <a href="https://html.spec.whatwg.org/multipage/browsers.html#unicode-serialisation-of-an-origin">Unicode serialisation</a> of the <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a> specified by the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#incumbent-settings-object">incumbent settings object</a>.</li>
            <li>Let the <a href="https://html.spec.whatwg.org/multipage/comms.html#dom-messageevent-source">source</a> attribute of <var>e</var> be initialized to a <code><a href="#service-worker-interface">ServiceWorker</a></code> object, setting its <a href="#dfn-service-worker-interface-client">service worker client</a> to <var>destination</var>'s <a href="#dfn-service-worker-container-interface-client">service worker client</a>, which represents the <a href="#dfn-service-worker-global-scope-service-worker">service worker</a> associated with the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#global-object">global object</a> specified by the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#incumbent-settings-object">incumbent settings object</a>.</li>
            <li>Let the <a href="https://html.spec.whatwg.org/multipage/comms.html#dom-messageevent-ports">ports</a> attribute of <var>e</var> be initialized to <var>newPorts</var>.</li>
            <li><a href="https://html.spec.whatwg.org/multipage/infrastructure.html#concept-event-dispatch">Dispatch</a> <var>e</var> at <var>destination</var>.</li>
          </ol>
          <p>The <a href="https://html.spec.whatwg.org/multipage/webappapis.html#concept-task">task</a> <em class="rfc2119" title="MUST">must</em> use the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#dom-manipulation-task-source">DOM manipulation task source</a>, and, for those where the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-loop">event loop</a> specified by the target <code><a href="#service-worker-container-interface">ServiceWorkerContainer</a></code> object's <a href="#dfn-service-worker-container-interface-client">service worker client</a> is a <a href="https://html.spec.whatwg.org/multipage/browsers.html#browsing-context">browsing context</a> <a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-loop">event loop</a>, <em class="rfc2119" title="MUST">must</em> be associated with the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#responsible-document">responsible document</a> specified by that target <code><a href="#service-worker-container-interface">ServiceWorkerContainer</a></code> object's <a href="#dfn-service-worker-container-interface-client">service worker client</a>.</p>
        </li>
      </ol>
      </div>
    </section>

    <section title="client-visibilitystate"><header><span class="section-number">4.2.5</span> <h4 id="client-visibilitystate" data-bookmark-label="4.2.5 visibilityState"><code>visibilityState</code></h4><span class="anchor"><a style="text-decoration: none;" href="#client-visibilitystate">¶</a></span></header>


      <p id="client-visibilitystate.1">The <dfn id="client-visibilitystate-attribute"><code>visibilityState</code></dfn> attribute <em class="rfc2119" title="MUST">must</em> return the <a href="https://dom.spec.whatwg.org/#context-object">context object</a>'s <a href="#dfn-service-worker-client-visibilitystate">visibility state</a>.</p>
    </section>

    <section title="client-focused"><header><span class="section-number">4.2.6</span> <h4 id="client-focused" data-bookmark-label="4.2.6 focused"><code>focused</code></h4><span class="anchor"><a style="text-decoration: none;" href="#client-focused">¶</a></span></header>


      <p id="client-focused.1">The <dfn id="client-focused-attribute"><code>focused</code></dfn> attribute <em class="rfc2119" title="MUST">must</em> return the <a href="https://dom.spec.whatwg.org/#context-object">context object</a>'s <a href="#dfn-service-worker-client-focusstate">focus state</a>.</p>
    </section>

    <section title="client-focus"><header><span class="section-number">4.2.7</span> <h4 id="client-focus" data-bookmark-label="4.2.7 focus()"><code>focus()</code></h4><span class="anchor"><a style="text-decoration: none;" href="#client-focus">¶</a></span></header>

      <p id="client-focus.1">The <dfn id="client-focus-method"><code>focus()</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>
      <div class="algorithm">
      <ol>
        <li>If this algorithm is not <a href="https://html.spec.whatwg.org/multipage/browsers.html#allowed-to-show-a-popup">allowed to show a popup</a>, return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with an "<code><a href="http://heycam.github.io/webidl/#invalidaccesserror">InvalidAccessError</a></code>" exception.</li>
        <li>Let <var>promise</var> be a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a>.</li>
        <li>Run these steps in parallel:
          <ol>
            <li>Let <var>browsingContext</var> be the <a href="https://dom.spec.whatwg.org/#context-object">context object</a>'s associated <a href="#dfn-service-worker-client-client">service worker client</a>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#global-object">global object</a>'s <a href="https://html.spec.whatwg.org/multipage/browsers.html#browsing-context">browsing context</a>.</li>
            <li><a href="https://html.spec.whatwg.org/multipage/webappapis.html#queue-a-task">Queue a task</a> to run the following substeps on the <a href="https://dom.spec.whatwg.org/#context-object">context object</a>'s associated <a href="#dfn-service-worker-client-client">service worker client</a>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#responsible-event-loop">responsible event loop</a> using the <a href="https://html.spec.whatwg.org/#user-interaction-task-source">user interaction task source</a>:
              <ol>
                <li>Run the <a href="https://html.spec.whatwg.org/multipage/interaction.html#focusing-steps">focusing steps</a> with <var>browsingContext</var>.</li>
                <li>Let <var>windowClient</var> be the result of running <a href="#capture-windowclient-algorithm">Capture Window Client</a> algorithm, or its <a href="#dfn-processing-equivalence">equivalent</a>, with <var>browsingContext</var> as the argument.</li>
                <li>If <var>windowClient</var>'s <a href="#dfn-service-worker-client-focusstate">focus state</a> is true, resolve <var>promise</var> with <var>windowClient</var>.</li>
                <li>Else, reject <var>promise</var> with a <code>TypeError</code>.</li>
              </ol>
            </li>
          </ol>
        </li>
        <li>Return <var>promise</var>.</li>
      </ol>
      </div>
    </section>

    <section title="client-navigate"><header><span class="section-number">4.2.8</span> <h4 id="client-navigate" data-bookmark-label="4.2.8 navigate(url)"><code>navigate(<var>url</var>)</code></h4><span class="anchor"><a style="text-decoration: none;" href="#client-navigate">¶</a></span></header>

      <p id="client-navigate.1">The <dfn id="client-navigate-method"><code>navigate()</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>
      <div class="algorithm">
      <ol>
        <li>Let <var>url</var> be the result of <a href="https://url.spec.whatwg.org/#concept-url-parser">parsing</a> <var>url</var> with <a href="https://html.spec.whatwg.org/multipage/webappapis.html#entry-settings-object">entry settings object</a>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#api-base-url">API base URL</a>.</li>
        <li>If <var>url</var> is failure, return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with a <code>TypeError</code>.</li>
        <li>If <var>url</var> is <code><a href="https://html.spec.whatwg.org/multipage/infrastructure.html#about:blank">about:blank</a></code>, return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with a <code>TypeError</code>.</li>
        <li>If the <a href="https://dom.spec.whatwg.org/#context-object">context object</a>'s associated <a href="#dfn-service-worker-client-client">service worker client</a>'s <a href="#dfn-service-worker-client-active-worker">active worker</a> is not the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#incumbent-settings-object">incumbent settings object</a>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#global-object">global object</a>'s <a href="#dfn-service-worker-global-scope-service-worker">service worker</a>, return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with a <code>TypeError</code>.</li>
        <li>Let <var>promise</var> be a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a>.</li>
        <li>Run these steps in parallel:
          <ol>
            <li>Let <var>browsingContext</var> be the <a href="https://dom.spec.whatwg.org/#context-object">context object</a>'s associated <a href="#dfn-service-worker-client-client">service worker client</a>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#global-object">global object</a>'s <a href="https://html.spec.whatwg.org/multipage/browsers.html#browsing-context">browsing context</a>.</li>
            <li>If <var>browsingContext</var> has <a href="https://html.spec.whatwg.org/multipage/browsers.html#discard-a-document">discarded</a> its <code><a href="https://html.spec.whatwg.org/multipage/dom.html#document">Document</a></code>, reject <var>promise</var> with a <code>TypeError</code> and abort these steps.</li>
            <li><a href="https://html.spec.whatwg.org/multipage/webappapis.html#queue-a-task">Queue a task</a> to run the following substeps on the <a href="https://dom.spec.whatwg.org/#context-object">context object</a>'s associated <a href="#dfn-service-worker-client-client">service worker client</a>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#responsible-event-loop">responsible event loop</a> using the <a href="https://html.spec.whatwg.org/#user-interaction-task-source">user interaction task source</a>:
              <ol>
                <li><a href="https://html.spec.whatwg.org/multipage/browsers.html#navigate">Navigate</a> <var>browsingContext</var> to <var>url</var> with <a href="https://html.spec.whatwg.org/multipage/browsers.html#replacement-enabled">replacement enabled</a> and <a href="https://html.spec.whatwg.org/multipage/browsers.html#exceptions-enabled">exceptions enabled</a>. The <a href="https://html.spec.whatwg.org/multipage/browsers.html#source-browsing-context">source browsing context</a> must be <var>browsingContext</var>.</li>
                <li>If the <a href="https://html.spec.whatwg.org/multipage/browsers.html#navigate">navigation</a> <a href="http://heycam.github.io/webidl/#dfn-throw">throws</a> an exception, reject <var>promise</var> with that exception and abort these steps.</li>
                <li>If the <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a> is not the <a href="https://html.spec.whatwg.org/multipage/browsers.html#same-origin">same</a> as the <a href="#dfn-service-worker-global-scope-service-worker">service worker</a>'s <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a>, then:
                  <ol>
                    <li>Resolve <var>promise</var> with null.</li>
                    <li>Abort these steps.</li>
                  </ol>
                </li>
                <li>Let <var>client</var> be the result of running <a href="#capture-windowclient-algorithm">Capture Window Client</a> algorithm, or its <a href="#dfn-processing-equivalence">equivalent</a>, with <var>browsingContext</var> as the argument.</li>
                <li>Resolve <var>promise</var> with <var>client</var>.</li>
              </ol>
            </li>
          </ol>
        </li>
        <li>Return <var>promise</var>.</li>
      </ol>
      </div>
    </section>
  </section>
  <section title="clients"><header><span class="section-number">4.3</span> <h3 id="clients" data-bookmark-label="4.3 Clients"><code>Clients</code></h3><span class="anchor"><a style="text-decoration: none;" href="#clients">¶</a></span></header>


<pre><code>[Exposed=ServiceWorker]
interface <dfn id="clients-interface" title="Clients">Clients</dfn> {
  // The objects returned will be new instances every time
  [NewObject] <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;sequence&lt;<a href="#client-interface">Client</a>&gt;&gt; <a href="#clients-matchall-method">matchAll</a>(optional <a href="#serviceworker-client-query-options-dictionary">ClientQueryOptions</a> <var>options</var>);
  [NewObject] <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;<a href="#window-client-interface">WindowClient</a>?&gt; <a href="#clients-openwindow-method">openWindow</a>(<a href="http://heycam.github.io/webidl/#idl-USVString">USVString</a> <var>url</var>);
  [NewObject] <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;void&gt; <a href="#clients-claim-method">claim</a>();
};

dictionary <dfn id="serviceworker-client-query-options-dictionary" title="ClientQueryOptions">ClientQueryOptions</dfn> {
  boolean includeUncontrolled = false;
  <a href="#client-type-enum">ClientType</a> type = "window";
};

enum <dfn id="client-type-enum" title="ClientType">ClientType</dfn> {
  "window",
  "worker",
  "sharedworker",
  "all"
};
</code></pre>
    <p id="clients.1">The <code><a href="#clients-interface">Clients</a></code> interface represents a container for a list of <code><a href="#client-interface">Client</a></code> objects.</p>
    <section title="clients-getall"><header><span class="section-number">4.3.1</span> <h4 id="clients-getall" data-bookmark-label="4.3.1 matchAll(options)"><code>matchAll(<var>options</var>)</code></h4><span class="anchor"><a style="text-decoration: none;" href="#clients-getall">¶</a></span></header>

      <p id="clients-getall.1">The <dfn id="clients-matchall-method"><code>matchAll(<var>options</var>)</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>
      <div class="algorithm">
      <ol>
        <li>Let <var>promise</var> be a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a>.</li>
        <li>Run these steps in parallel:
          <ol>
            <li>Let <var>clients</var> be an empty array.</li>
            <li>If the optional argument <var>options</var> is omitted, then:
              <ol>
                <li>For each <a href="#dfn-service-worker-client">service worker client</a> <var>client</var> whose <a href="#dfn-service-worker-client-active-worker">active worker</a> is the associated <a href="#dfn-service-worker-global-scope-service-worker">service worker</a>, in the most recently <a href="https://html.spec.whatwg.org/multipage/interaction.html#focusing-steps">focused</a> order for <a href="#dfn-window-client">window clients</a>:
                  <ol>
                    <li>If <var>client</var> is a <a href="#dfn-window-client">window client</a>, then:
                      <ol>
                        <li>Let <var>windowClient</var> be the result of running <a href="#capture-windowclient-algorithm">Capture Window Client</a> algorithm, or its <a href="#dfn-processing-equivalence">equivalent</a>, with <var>client</var>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#responsible-browsing-context">responsible browsing context</a> as the argument.</li>
                        <li>Add <var>windowClient</var> to <var>clients</var>.</li>
                      </ol>
                    </li>
                  </ol>
                </li>
                <li>Resolve <var>promise</var> with <var>clients</var>.</li>
              </ol>
            </li>
            <li>Else:
              <ol>
                <li>Let <var>targetClients</var> be an empty array.</li>
                <li>For each <a href="#dfn-service-worker-client">service worker client</a> <var>client</var> whose <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a> is the <a href="https://html.spec.whatwg.org/multipage/browsers.html#same-origin">same</a> as the associated <a href="#dfn-service-worker-global-scope-service-worker">service worker</a>'s <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a>:
                  <ol>
                    <li>If <var>options</var>.<var>includeUncontrolled</var> is false, then:
                      <ol>
                        <li>If <var>client</var>'s <a href="#dfn-service-worker-client-active-worker">active worker</a> is the associated <a href="#dfn-service-worker-global-scope-service-worker">service worker</a>, add <var>client</var> to <var>targetClients</var>.</li>
                      </ol>
                    </li>
                    <li>Else:
                      <ol>
                        <li>Add <var>client</var> to <var>targetClients</var>.</li>
                      </ol>
                    </li>
                  </ol>
                </li>
                <li>Let <var>matchedClients</var> be an empty array.</li>
                <li>For each <a href="#dfn-service-worker-client">service worker client</a> <var>client</var> in <var>targetClients</var>, in the most recently <a href="https://html.spec.whatwg.org/multipage/interaction.html#focusing-steps">focused</a> order for <a href="#dfn-window-client">window clients</a>:
                  <ol>
                    <li>If <var>options</var>.<var>type</var> is "<code>window</code>", and <var>client</var> is a <a href="#dfn-window-client">window client</a>, then:
                      <ol>
                        <li>Let <var>windowClient</var> be the result of running <a href="#capture-windowclient-algorithm">Capture Window Client</a> algorithm, or its <a href="#dfn-processing-equivalence">equivalent</a>, with <var>client</var>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#responsible-browsing-context">responsible browsing context</a> as the argument.</li>
                        <li>Add <var>windowClient</var> to <var>matchedClients</var>.</li>
                      </ol>
                    </li>
                    <li>Else if <var>options</var>.<var>type</var> is "<code>worker</code>" and <var>client</var> is a <a href="#dfn-dedicatedworker-client">dedicated worker client</a>, add a <code><a href="#client-interface">Client</a></code> object that represents <var>client</var> to <var>matchedClients</var>.</li>
                    <li>Else if <var>options</var>.<var>type</var> is "<code>sharedworker</code>" and <var>client</var> is a <a href="#dfn-sharedworker-client">shared worker client</a>, add a <code><a href="#client-interface">Client</a></code> object that represents <var>client</var> to <var>matchedClients</var>.</li>
                    <li>Else if <var>options</var>.<var>type</var> is "<code>all</code>", then:
                      <ol>
                        <li>If <var>client</var> is a <a href="#dfn-window-client">window client</a>, then:
                          <ol>
                            <li>Let <var>windowClient</var> be the result of running <a href="#capture-windowclient-algorithm">Capture Window Client</a> algorithm, or its <a href="#dfn-processing-equivalence">equivalent</a>, with <var>client</var>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#responsible-browsing-context">responsible browsing context</a> as the argument.</li>
                            <li>Add <var>windowClient</var> to <var>matchedClients</var>.</li>
                          </ol>
                        </li>
                        <li>Else, add a <code><a href="#client-interface">Client</a></code> object that represents <var>client</var> to <var>matchedClients</var>.</li>
                      </ol>
                  </li></ol>
                </li>
                <li>Resolve <var>promise</var> with <var>matchedClients</var>.</li>
              </ol>
            </li>
          </ol>
        </li>
        <li>Return <var>promise</var>.</li>
      </ol>
      </div>
    </section>
    <section title="clients-openwindow"><header><span class="section-number">4.3.2</span> <h4 id="clients-openwindow" data-bookmark-label="4.3.2 openWindow(url)"><code>openWindow(<var>url</var>)</code></h4><span class="anchor"><a style="text-decoration: none;" href="#clients-openwindow">¶</a></span></header>

      <p id="clients-openwindow.1">The <dfn id="clients-openwindow-method"><code>openWindow(<var>url</var>)</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>
      <div class="algorithm">
      <ol>
        <li>Let <var>url</var> be the result of <a href="https://url.spec.whatwg.org/#concept-url-parser">parsing</a> <var>url</var> with <a href="https://html.spec.whatwg.org/multipage/webappapis.html#entry-settings-object">entry settings object</a>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#api-base-url">API base URL</a>.</li>
        <li>If <var>url</var> is failure, return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with a <code>TypeError</code>.</li>
        <li>If <var>url</var> is <code><a href="https://html.spec.whatwg.org/multipage/infrastructure.html#about:blank">about:blank</a></code>, return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with a <code>TypeError</code>.</li>
        <li>If this algorithm is not <a href="https://html.spec.whatwg.org/multipage/browsers.html#allowed-to-show-a-popup">allowed to show a popup</a>, return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with an "<code><a href="http://heycam.github.io/webidl/#invalidaccesserror">InvalidAccessError</a></code>" exception.</li>
        <li>Let <var>promise</var> be a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a>.</li>
        <li>Run these steps in parallel:
          <ol>
            <li>Let <var>newContext</var> be a new <a href="https://html.spec.whatwg.org/multipage/browsers.html#top-level-browsing-context">top level browsing context</a>.</li>
            <li><a href="https://html.spec.whatwg.org/multipage/browsers.html#navigate">Navigate</a> <var>newContext</var> to <var>url</var>, with <a href="https://html.spec.whatwg.org/multipage/browsers.html#exceptions-enabled">exceptions enabled</a> and <a href="https://html.spec.whatwg.org/multipage/browsers.html#replacement-enabled">replacement enabled</a>.</li>
            <li>If the <a href="https://html.spec.whatwg.org/multipage/browsers.html#navigate">navigation</a> <a href="http://heycam.github.io/webidl/#dfn-throw">throws</a> an exception, reject <var>promise</var> with that exception and abort these steps.</li>
            <li>If the <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a> is not the <a href="https://html.spec.whatwg.org/multipage/browsers.html#same-origin">same</a> as the <a href="#dfn-service-worker-global-scope-service-worker">service worker</a>'s <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a>, then:
              <ol>
                <li>Resolve <var>promise</var> with null.</li>
                <li>Abort these steps.</li>
              </ol>
            </li>
            <li>Let <var>client</var> be the result of running <a href="#capture-windowclient-algorithm">Capture Window Client</a> algorithm, or its <a href="#dfn-processing-equivalence">equivalent</a>, with <var>newContext</var> as the argument.</li>
            <li>Resolve <var>promise</var> with <var>client</var>.</li>
          </ol>
        </li>
        <li>Return <var>promise</var>.</li>
      </ol>
      </div>
    </section>

    <section title="clients-claim"><header><span class="section-number">4.3.3</span> <h4 id="clients-claim" data-bookmark-label="4.3.3 claim()"><code>claim()</code></h4><span class="anchor"><a style="text-decoration: none;" href="#clients-claim">¶</a></span></header>

      <p id="clients-claim.1">The <dfn id="clients-claim-method"><code>claim()</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>
      <div class="algorithm">
      <ol>
        <li>If the <a href="#dfn-service-worker-global-scope-service-worker">service worker</a> is not an <a href="#dfn-active-worker">active worker</a>, return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with an "<code><a href="http://heycam.github.io/webidl/#invalidstateerror">InvalidStateError</a></code>" exception.</li>
        <li>Let <var>promise</var> be a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a>.</li>
        <li>Run the following substeps in parallel:
          <ol>
            <li>For each <a href="#dfn-service-worker-client">service worker client</a> <var>client</var> whose <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a> is the <a href="https://html.spec.whatwg.org/multipage/browsers.html#same-origin">same</a> as the <a href="#dfn-service-worker-global-scope-service-worker">service worker</a>'s <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a>:
              <ol>
                <li>Let <var>registration</var> be the result of running <a href="#scope-match-algorithm">Match Service Worker Registration</a> algorithm passing <var>client</var>'s <a href="https://www.w3.org/Bugs/Public/show_bug.cgi?id=27146">creation url</a> as the argument.</li>
                <li>If <var>registration</var> is not the <a href="#dfn-service-worker-global-scope-service-worker">service worker</a>'s <a href="#dfn-containing-service-worker-registration">containing service worker registration</a>, continue to the next iteration of the loop.</li>
                <li>If <var>client</var>'s <a href="#dfn-active-worker">active worker</a> is not the <a href="#dfn-service-worker-global-scope-service-worker">service worker</a>, then:
                  <ol>
                    <li>Invoke <a href="#on-client-unload-algorithm">Handle Service Worker Client Unload</a> with <var>client</var> as the argument.</li>
                    <li>Set <var>client</var>'s <a href="#dfn-active-worker">active worker</a> to <a href="#dfn-service-worker-global-scope-service-worker">service worker</a>.</li>
                    <li>Invoke <a href="#notify-controller-change-algorithm">Notify Controller Change</a> algorithm with <var>client</var> as the argument.</li>
                  </ol>
                </li>
              </ol>
            </li>
            <li>Resolve <var>promise</var> with undefined.</li>
          </ol>
        </li>
        <li>Return <var>promise</var>.</li>
      </ol>
      </div>
    </section>
  </section>



  <section title="extendable-event"><header><span class="section-number">4.4</span> <h3 id="extendable-event" data-bookmark-label="4.4 ExtendableEvent"><code>ExtendableEvent</code></h3><span class="anchor"><a style="text-decoration: none;" href="#extendable-event">¶</a></span></header>


<pre><code>[Constructor(DOMString <var>type</var>, optional <a href="#extendable-event-init-dictionary">ExtendableEventInit</a> <var>eventInitDict</var>), Exposed=ServiceWorker]
interface <dfn id="extendable-event-interface" title="ExtendableEvent">ExtendableEvent</dfn> : <a href="https://dom.spec.whatwg.org/#event">Event</a> {
  void <a href="#extendable-event-waituntil-method">waitUntil</a>(<a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;any&gt; <var>f</var>);
};

dictionary <dfn id="extendable-event-init-dictionary" title="ExtendableEventInit">ExtendableEventInit</dfn> : <a href="https://dom.spec.whatwg.org/#dictdef-eventinit">EventInit</a> {
  // Defined for the forward compatibility across the derived events
};
</code></pre>

    <p id="extendable-event.1">An <code><a href="#extendable-event-interface" title="ExtendableEvent">ExtendableEvent</a></code> object has an associated <dfn id="dfn-extend-lifetime-promises">extend lifetime promises</dfn> (an array of <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promises</a>). It is initially set to null.</p>

    <p id="extendable-event.2"><a href="#dfn-service-worker">Service workers</a> have two <a href="#dfn-lifecycle-events">lifecycle events</a>, <code><a href="#service-worker-global-scope-install-event">install</a></code> and <code><a href="#service-worker-global-scope-activate-event">activate</a></code>. <a href="#dfn-service-worker">Service workers</a> use the <code><a href="#extendable-event-interface">ExtendableEvent</a></code> interface for <code><a href="#service-worker-global-scope-activate-event">activate</a></code> event and <code><a href="#service-worker-global-scope-install-event">install</a></code> event.</p>

    <p id="extendable-event.3"><a href="#extensibility">Service worker extensions</a> that <a href="#extension-to-service-worker-global-scope">define event handlers</a> <em class="rfc2119" title="MAY">may</em> also use or extend the <code><a href="#extendable-event-interface">ExtendableEvent</a></code> interface.</p>

    <section title="wait-until-method"><header><span class="section-number">4.4.1</span> <h4 id="wait-until-method" data-bookmark-label="4.4.1 event.waitUntil(f)"><code>event.waitUntil(<var>f</var>)</code></h4><span class="anchor"><a style="text-decoration: none;" href="#wait-until-method">¶</a></span></header>


      <p id="wait-until-method.1"><code><a href="#extendable-event-waituntil-method">waitUntil(<var>f</var>)</a></code> method extends the lifetime of the event.</p>

      <p id="wait-until-method.2"><dfn id="extendable-event-waituntil-method"><code>waitUntil(<var>f</var>)</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>
      <div class="algorithm">
      <ol>
        <li>If the <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-execution-contexts">active function</a> is not the callback of the <a href="https://dom.spec.whatwg.org/#concept-event-listener">event handler</a> whose type is the <a href="https://dom.spec.whatwg.org/#context-object">context object</a>'s <a href="https://dom.spec.whatwg.org/#dom-event-type">type</a> value, then:
          <ol>
            <li><a href="http://heycam.github.io/webidl/#dfn-throw">Throw</a> an "<code><a href="http://heycam.github.io/webidl/#invalidstateerror">InvalidStateError</a></code>" exception.</li>
            <li>Abort these steps.</li>
          </ol>
        </li>
        <li>Add <var>f</var> to <a href="#dfn-extend-lifetime-promises">extend lifetime promises</a>.</li>
      </ol>
      </div>

      <p id="wait-until-method.3">In the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#concept-task">task</a> <var>task</var> in which the steps of <code><a href="#extendable-event-waituntil-method">waitUntil(<var>f</var>)</a></code> is running, the user agent <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>
      <div class="algorithm">
      <ol>
        <li>Let <var>extendLifetimePromises</var> be an empty array.</li>
        <li>For each <a href="https://dom.spec.whatwg.org/#concept-event-listener">event listener</a> <a href="https://dom.spec.whatwg.org/#concept-event-listener-invoke">invoked</a>:
          <ol>
            <li>Let <var>eventObject</var> be the first argument passed to this <a href="https://dom.spec.whatwg.org/#concept-event-listener">event listener</a>.</li>
            <li>Append <var>eventObject</var>'s <a href="#dfn-extend-lifetime-promises">extend lifetime promises</a> to <var>extendLifetimePromises</var>.</li>
          </ol>
        </li>
        <li>Do not <a href="https://html.spec.whatwg.org/multipage/workers.html#terminate-a-worker">terminate</a> the <a href="#dfn-service-worker">service worker</a> whose <a href="https://html.spec.whatwg.org/multipage/webappapis.html#responsible-event-loop">responsible event loop</a> is running <var>task</var> until <a href="http://www.w3.org/2001/tag/doc/promises-guide#waiting-for-all">waiting for all of</a> <var>extendLifetimePromises</var> settles.</li>
      </ol>
      </div>
      <p id="wait-until-method.4">However, the user agent <em class="rfc2119" title="MAY">may</em> impose a time limit to this lifetime extension.</p>

      <p id="wait-until-method.5"><a href="#dfn-service-worker">Service workers</a> and <a href="#extensibility">extensions</a> that <a href="#extension-to-service-worker-global-scope">define event handlers</a> <em class="rfc2119" title="MAY">may</em> define their own behaviours, allowing the <a href="#dfn-extend-lifetime-promises">extend lifetime promises</a> to suggest operation length, and the rejected state of any of the <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> in <a href="#dfn-extend-lifetime-promises">extend lifetime promises</a> to suggest operation failure.</p>

      <p id="wait-until-method.6"><a href="#dfn-service-worker">Service workers</a> define the following behaviours for <code><a href="#service-worker-global-scope-install-event">install</a></code> event and <code><a href="#service-worker-global-scope-activate-event">activate</a></code> event:
        </p><ul>
          <li>When called in <code><a href="#service-worker-global-scope-oninstall-attribute">oninstall</a></code>, it delays treating the <a href="#dfn-installing-worker">installing worker</a> as <em><a href="#dfn-state">installed</a></em> (i.e. a <a href="#dfn-waiting-worker">waiting worker</a>) until the passed <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> <var>f</var> resolves successfully. If <var>f</var> rejects, the installation fails. (See step 11.6.2 of <a href="#installation-algorithm">Install</a> algorithm). This is primarily used to ensure that a <a href="#dfn-service-worker">service worker</a> is not considered <em><a href="#dfn-state">installed</a></em> (i.e. a <a href="#dfn-waiting-worker">waiting worker</a>) until all of the core caches it depends on are populated.</li>
          <li>When called in <code><a href="#service-worker-global-scope-onactivate-attribute">onactivate</a></code>, it delays treating the <a href="#dfn-active-worker">active worker</a> as <em><a href="#dfn-state">activated</a></em> until the passed <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> <var>f</var> settles. (See step 16 of <a href="#activation-algorithm">Activate</a> algorithm). This is primarily used to ensure that any <a href="#dfn-functional-events">functional events</a> are not dispatched to the <code><a href="#service-worker-global-scope-interface">ServiceWorkerGlobalScope</a></code> object that represents the <a href="#dfn-service-worker">service worker</a> until it upgrades database schemas and deletes the outdated cache entries.</li>
        </ul>
      <p id="wait-until-method.7"></p>
    </section>
  </section>

  <section title="fetch-event-section"><header><span class="section-number">4.5</span> <h3 id="fetch-event-section" data-bookmark-label="4.5 FetchEvent"><code>FetchEvent</code></h3><span class="anchor"><a style="text-decoration: none;" href="#fetch-event-section">¶</a></span></header>


<pre><code>[Constructor(DOMString <var>type</var>, optional <a href="#fetch-event-init-dictionary">FetchEventInit</a> <var>eventInitDict</var>), Exposed=ServiceWorker]
interface <dfn id="fetch-event-interface" title="FetchEvent">FetchEvent</dfn> : <a href="#extendable-event-interface">ExtendableEvent</a> {
  [SameObject] readonly attribute <a href="https://fetch.spec.whatwg.org/#request">Request</a> <a href="#fetch-event-request-attribute">request</a>;
  [SameObject] readonly attribute <a href="#client-interface">Client</a> <a href="#fetch-event-client-attribute">client</a>;
  readonly attribute boolean <a href="#fetch-event-isreload-attribute">isReload</a>;

  void <a href="#fetch-event-respondwith-method">respondWith</a>((<a href="https://fetch.spec.whatwg.org/#response">Response</a> or <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;<a href="https://fetch.spec.whatwg.org/#response">Response</a>&gt;) <var>r</var>);
};

dictionary <dfn id="fetch-event-init-dictionary" title="FetchEventInit">FetchEventInit</dfn> : <a href="#extendable-event-init-dictionary">ExtendableEventInit</a> {
  <a href="https://fetch.spec.whatwg.org/#request">Request</a> request;
  <a href="#client-interface">Client</a> client;
  boolean isReload = false;
};
</code></pre>
    <p id="fetch-event-section.1"><a href="#dfn-service-worker">Service workers</a> have an essential <a href="#dfn-functional-events">functional event</a> <code><a href="#service-worker-global-scope-fetch-event">fetch</a></code>. For <code><a href="#service-worker-global-scope-fetch-event">fetch</a></code> event, <a href="#dfn-service-worker">service workers</a> use the <code><a href="#extendable-event-interface">FetchEvent</a></code> interface which extends the <code><a href="#extendable-event-interface">ExtendableEvent</a></code> interface.</p>

    <p id="fetch-event-section.2">Each event using <code><a href="#fetch-event-interface">FetchEvent</a></code> interface has the following associated flag that is initially unset:
      </p><ul>
        <li><dfn id="wait-to-respond-flag">wait to respond flag</dfn></li>
        <li><dfn id="respond-with-entered-flag">respond-with entered flag</dfn></li>
        <li><dfn id="respond-with-error-flag">respond-with error flag</dfn></li>
      </ul>
    <p id="fetch-event-section.3"></p>

    <section title="fetch-event-request"><header><span class="section-number">4.5.1</span> <h4 id="fetch-event-request" data-bookmark-label="4.5.1 event.request"><code>event.request</code></h4><span class="anchor"><a style="text-decoration: none;" href="#fetch-event-request">¶</a></span></header>


      <p id="fetch-event-request.1"><dfn id="fetch-event-request-attribute"><code>request</code></dfn> attribute <em class="rfc2119" title="MUST">must</em> return the value it was initialized to.</p>
    </section>

    <section title="fetch-event-client"><header><span class="section-number">4.5.2</span> <h4 id="fetch-event-client" data-bookmark-label="4.5.2 event.client"><code>event.client</code></h4><span class="anchor"><a style="text-decoration: none;" href="#fetch-event-client">¶</a></span></header>


      <p id="fetch-event-client.1"><dfn id="fetch-event-client-attribute"><code>client</code></dfn> attribute <em class="rfc2119" title="MUST">must</em> return the value it was initialized to.</p>
    </section>

    <section title="is-reload-attribute"><header><span class="section-number">4.5.3</span> <h4 id="is-reload-attribute" data-bookmark-label="4.5.3 event.isReload"><code>event.isReload</code></h4><span class="anchor"><a style="text-decoration: none;" href="#is-reload-attribute">¶</a></span></header>


      <p id="is-reload-attribute.1"><dfn id="fetch-event-isreload-attribute"><code>isReload</code></dfn> attribute <em class="rfc2119" title="MUST">must</em> return the value it was initialized to. When an <a href="https://dom.spec.whatwg.org/#concept-event">event</a> is created the attribute <em class="rfc2119" title="MUST">must</em> be initialized to false.</p>
      <p class="note" id="is-reload-attribute.2">Pressing the refresh button should be considered a reload while clicking a link and pressing the back button should not. The behavior of the <var>Ctrl+l enter</var> is left to the implementations of the user agents.</p>
    </section>

    <section title="respond-with-method"><header><span class="section-number">4.5.4</span> <h4 id="respond-with-method" data-bookmark-label="4.5.4 event.respondWith(r)"><code>event.respondWith(r)</code></h4><span class="anchor"><a style="text-decoration: none;" href="#respond-with-method">¶</a></span></header>


      <p id="respond-with-method.1">When <code><a href="#fetch-event-respondwith-method">event.respondWith(<var>r</var>)</a></code> method is invoked, the argument, <var>r</var>, <em class="rfc2119" title="MUST">must</em> resolve with a <code><a href="https://fetch.spec.whatwg.org/#response">Response</a></code>, else a <a href="https://fetch.spec.whatwg.org/#concept-network-error">network error</a> is returned to <a href="https://fetch.spec.whatwg.org/#concept-fetch">Fetch</a>. If the request is a top-level navigation and the return value is a <code><a href="https://fetch.spec.whatwg.org/#response">Response</a></code> whose <code>type</code> attribute is "<code>opaque</code>" (i.e., an opaque response body), a <a href="https://fetch.spec.whatwg.org/#concept-network-error">network error</a> is returned to <a href="https://fetch.spec.whatwg.org/#concept-fetch">Fetch</a>. The final URL of all successful (non network-error) responses is the <a href="https://fetch.spec.whatwg.org/#concept-request-url">requested</a> URL. Renderer-side security checks about tainting for cross-origin content are tied to the transparency (or opacity) of the <code><a href="https://fetch.spec.whatwg.org/#response">Response</a></code> body, not URLs.</p>

      <p id="respond-with-method.2"><dfn id="fetch-event-respondwith-method"><code>respondWith(<var>r</var>)</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>
      <div class="algorithm">
      <ol>
        <li>If the <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-execution-contexts">active function</a> is not the callback of the <a href="https://dom.spec.whatwg.org/#concept-event-listener">event handler</a> whose type is <a href="#service-worker-global-scope-fetch-event">fetch</a>, then:
          <ol>
            <li><a href="http://heycam.github.io/webidl/#dfn-throw">Throw</a> an "<code><a href="http://heycam.github.io/webidl/#invalidstateerror">InvalidStateError</a></code>" exception.</li>
            <li>Abort these steps.</li>
          </ol>
        </li>
        <li>If the <a href="#respond-with-entered-flag">respond-with entered flag</a> is set, then:
          <ol>
            <li><a href="http://heycam.github.io/webidl/#dfn-throw">Throw</a> an "<code><a href="http://heycam.github.io/webidl/#invalidstateerror">InvalidStateError</a></code>" exception.</li>
            <li>Abort these steps.</li>
          </ol>
        </li>
        <li>Set the <a href="https://dom.spec.whatwg.org/#stop-propagation-flag">stop propagation flag</a> and <a href="https://dom.spec.whatwg.org/#stop-immediate-propagation-flag">stop immediate propagation flag</a>.</li>
        <li>Set the <a href="#respond-with-entered-flag">respond-with entered flag</a>.</li>
        <li>Set the <a href="#wait-to-respond-flag">wait to respond flag</a>.</li>
        <li>Let <var>responsePromise</var> be null.</li>
        <li>If <var>r</var> is a <code><a href="https://fetch.spec.whatwg.org/#response">Response</a></code> object, then:
          <ol>
            <li>Set <var>responsePromise</var> to a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> resolved with <var>r</var>.</li>
          </ol>
        </li>
        <li>Else:
          <ol>
            <li>Set <var>responsePromise</var> to <var>r</var>.</li>
          </ol>
        </li>
        <li>Run the following substeps in parallel:
          <ol>
            <li>Wait until <var>responsePromise</var> settles.</li>
            <li>If <var>responsePromise</var> rejected, then:
              <ol>
                <li>Set the <a href="#respond-with-error-flag">respond-with error flag</a>.</li>
              </ol>
            </li>
            <li>If <var>responsePromise</var> resolved with <var>response</var>, then:
              <ol>
                <li>If <var>response</var> is a <code><a href="https://fetch.spec.whatwg.org/#response">Response</a></code> object, then:
                  <ol>
                    <li>Let <var>request</var> be the <a href="https://dom.spec.whatwg.org/#context-object">context object</a>'s <code>request</code> attribute value.</li>
                    <li>If <var>response</var>.<var>type</var> is "<code>opaque</code>", and <var>request</var>'s associated <a href="https://fetch.spec.whatwg.org/#concept-request-request">request</a> is a <a href="https://fetch.spec.whatwg.org/#client-request">client request</a>, set the <a href="#respond-with-error-flag">respond-with error flag</a>.</li>
                    <li>If <var>response</var>'s <a href="https://fetch.spec.whatwg.org/#concept-body-body">body</a> is non-null, then:
                      <ol>
                        <li>If <var>response</var>'s <a href="https://fetch.spec.whatwg.org/#concept-body-used-flag">used flag</a> is set, set the <a href="#respond-with-error-flag">respond-with error flag</a>.</li>
                        <li>Set <var>response</var>'s <a href="https://fetch.spec.whatwg.org/#concept-body-used-flag">used flag</a>.</li>
                      </ol>
                    </li>
                  </ol>
                </li>
                <li>Else:
                  <ol>
                    <li>Set the <a href="#respond-with-error-flag">respond-with error flag</a>.</li>
                  </ol>
                  <p class="note">If the <a href="#respond-with-error-flag">respond-with error flag</a> is set, a <a href="https://fetch.spec.whatwg.org/#concept-network-error">network error</a> is returned to <a href="https://fetch.spec.whatwg.org/#concept-fetch">Fetch</a> through <a href="#on-fetch-request-algorithm">Handle Fetch</a> algorithm. (See the step 21.1.) Otherwise, the value <var>response</var> is returned to <a href="https://fetch.spec.whatwg.org/#concept-fetch">Fetch</a> through <a href="#on-fetch-request-algorithm">Handle Fetch</a> algorithm. (See the step 22.1.)</p>
                </li>
              </ol>
            </li>
            <li>Unset the <a href="#wait-to-respond-flag">wait to respond flag</a>.</li>
          </ol>
        </li>
      </ol>
      </div>
    </section>
  </section>

  <section title="extendablemessage-event-section"><header><span class="section-number">4.6</span> <h3 id="extendablemessage-event-section" data-bookmark-label="4.6 ExtendableMessageEvent"><code>ExtendableMessageEvent</code></h3><span class="anchor"><a style="text-decoration: none;" href="#extendablemessage-event-section">¶</a></span></header>


<pre><code>[Constructor(DOMString <var>type</var>, optional <a href="#extendablemessage-event-init-dictionary">ExtendableMessageEventInit</a> <var>eventInitDict</var>), Exposed=ServiceWorker]
interface <dfn id="extendablemessage-event-interface" title="ExtendableMessageEvent">ExtendableMessageEvent</dfn> : <a href="#extendable-event-interface">ExtendableEvent</a> {
  readonly attribute any <a href="#extendablemessage-event-data-attribute">data</a>;
  readonly attribute DOMString <a href="#extendablemessage-event-origin-attribute">origin</a>;
  readonly attribute DOMString <a href="#extendablemessage-event-lasteventid-attribute">lastEventId</a>;
  [SameObject] readonly attribute (<a href="#client-interface">Client</a> or <a href="#service-worker-interface">ServiceWorker</a> or <a href="https://html.spec.whatwg.org/multipage/comms.html#messageport">MessagePort</a>)? <a href="#extendablemessage-event-source-attribute">source</a>;
  [SameObject] readonly attribute <a href="https://html.spec.whatwg.org/multipage/comms.html#messageport">MessagePort</a>[]? <a href="#extendablemessage-event-ports-attribute">ports</a>;
};

dictionary <dfn id="extendablemessage-event-init-dictionary" title="ExtendableMessageEventInit">ExtendableMessageEventInit</dfn> : <a href="#extendable-event-init-dictionary">ExtendableEventInit</a> {
  any data;
  DOMString origin;
  DOMString lastEventId;
  (<a href="#client-interface">Client</a> or <a href="#service-worker-interface">ServiceWorker</a> or <a href="https://html.spec.whatwg.org/multipage/comms.html#messageport">MessagePort</a>)? source;
  sequence&lt;<a href="https://html.spec.whatwg.org/multipage/comms.html#messageport">MessagePort</a>&gt; ports;
};
</code></pre>
    <p id="extendablemessage-event-section.1"><a href="#dfn-service-worker">Service workers</a> define the <a href="#extendable-event-waituntil-method">extendable</a> <a href="#service-worker-global-scope-message-event">message</a> event that extends the <a href="https://html.spec.whatwg.org/multipage/indices.html#event-message">message</a> event defined in <a href="https://html.spec.whatwg.org/">HTML</a> to allow extending the lifetime of the event. For the <a href="#service-worker-global-scope-message-event">message</a> event, <a href="#dfn-service-worker">service workers</a> use the <code><a href="#extendablemessage-event-interface">ExtendableMessageEvent</a></code> interface which extends the <code><a href="#extendable-event-interface">ExtendableEvent</a></code> interface.</p>

    <section title="extendablemessage-event-data"><header><span class="section-number">4.6.1</span> <h4 id="extendablemessage-event-data" data-bookmark-label="4.6.1 event.data"><code>event.data</code></h4><span class="anchor"><a style="text-decoration: none;" href="#extendablemessage-event-data">¶</a></span></header>

      <p id="extendablemessage-event-data.1">The <dfn id="extendablemessage-event-data-attribute">data</dfn> attribute <em class="rfc2119" title="MUST">must</em> return the value it was initialized to. When the object is created, this attribute <em class="rfc2119" title="MUST">must</em> be initialized to null. It represents the message being sent.</p>
    </section>

    <section title="extendablemessage-event-origin"><header><span class="section-number">4.6.2</span> <h4 id="extendablemessage-event-origin" data-bookmark-label="4.6.2 event.origin"><code>event.origin</code></h4><span class="anchor"><a style="text-decoration: none;" href="#extendablemessage-event-origin">¶</a></span></header>

      <p id="extendablemessage-event-origin.1">The <dfn id="extendablemessage-event-origin-attribute">origin</dfn> attribute <em class="rfc2119" title="MUST">must</em> return the value it was initialized to. When the object is created, this attribute <em class="rfc2119" title="MUST">must</em> be initialized to the empty string. It represents the <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a> of the <a href="#dfn-service-worker-client">service worker client</a> that sent the message.</p>
    </section>

    <section title="extendablemessage-event-lasteventid"><header><span class="section-number">4.6.3</span> <h4 id="extendablemessage-event-lasteventid" data-bookmark-label="4.6.3 event.lastEventId"><code>event.lastEventId</code></h4><span class="anchor"><a style="text-decoration: none;" href="#extendablemessage-event-lasteventid">¶</a></span></header>

      <p id="extendablemessage-event-lasteventid.1">The <dfn id="extendablemessage-event-lasteventid-attribute">lastEventId</dfn> attribute <em class="rfc2119" title="MUST">must</em> return the value it was initialized to. When the object is created, this attribute <em class="rfc2119" title="MUST">must</em> be initialized to the empty string.</p>
    </section>

    <section title="extendablemessage-event-source"><header><span class="section-number">4.6.4</span> <h4 id="extendablemessage-event-source" data-bookmark-label="4.6.4 event.source"><code>event.source</code></h4><span class="anchor"><a style="text-decoration: none;" href="#extendablemessage-event-source">¶</a></span></header>

      <p id="extendablemessage-event-source.1">The <dfn id="extendablemessage-event-source-attribute">source</dfn> attribute <em class="rfc2119" title="MUST">must</em> return the value it was initialized to. When the object is created, this attribute <em class="rfc2119" title="MUST">must</em> be initialized to null. It represents the <code><a href="#client-interface">Client</a></code> object from which the message is sent.</p>

      <p class="note" id="extendablemessage-event-source.2">When <a href="https://github.com/mkruisselbrink/navigator-connect/">navigator.connect() API</a> extends the communication model between cross origin service workers, this attribute may also represent <a href="https://mkruisselbrink.github.io/navigator-connect/#idl-def-ServicePort">ServicePort</a> object from which the message is sent.</p>
    </section>

    <section title="extendablemessage-event-ports"><header><span class="section-number">4.6.5</span> <h4 id="extendablemessage-event-ports" data-bookmark-label="4.6.5 event.ports"><code>event.ports</code></h4><span class="anchor"><a style="text-decoration: none;" href="#extendablemessage-event-ports">¶</a></span></header>

      <p id="extendablemessage-event-ports.1">The <dfn id="extendablemessage-event-ports-attribute">ports</dfn> attribute <em class="rfc2119" title="MUST">must</em> return the value it was initialized to. When the object is created, this attribute <em class="rfc2119" title="MUST">must</em> be initialized to null. It represents the <a href="https://html.spec.whatwg.org/multipage/comms.html#messageport">MessagePort</a> array being sent, if any.</p>
    </section>
  </section>

  <section title="execution-context-events"><header><span class="section-number">4.7</span> <h3 id="execution-context-events" data-bookmark-label="4.7 Events">Events</h3><span class="anchor"><a style="text-decoration: none;" href="#execution-context-events">¶</a></span></header>


    <p id="execution-context-events.1">The following events are dispatched on <a href="#service-worker-global-scope-interface">ServiceWorkerGlobalScope</a> object:</p>

    <table>
      <thead>
        <tr>
          <th>Event name</th>
          <th>Interface</th>
          <th>Dispatched when…</th>
        </tr>
      </thead>
      <tbody>
        <tr>
          <td><dfn id="service-worker-global-scope-install-event"><code>install</code></dfn></td>
          <td><code><a href="#extendable-event-interface">ExtendableEvent</a></code></td>
          <td>[<a href="#dfn-lifecycle-events">Lifecycle event</a>] The <a href="#dfn-service-worker-global-scope-service-worker">service worker</a>'s <a href="#dfn-containing-service-worker-registration">containing service worker registration</a>'s <a href="#dfn-installing-worker">installing worker</a> changes. (See step 11.2 of the <a href="#installation-algorithm">Install</a> algorithm.)</td>
        </tr>
        <tr>
          <td><dfn id="service-worker-global-scope-activate-event"><code>activate</code></dfn></td>
          <td><code><a href="#extendable-event-interface">ExtendableEvent</a></code></td>
          <td>[<a href="#dfn-lifecycle-events">Lifecycle event</a>] The <a href="#dfn-service-worker-global-scope-service-worker">service worker</a>'s <a href="#dfn-containing-service-worker-registration">containing service worker registration</a>'s <a href="#dfn-active-worker">active worker</a> changes. (See step 15.2 of the <a href="#activation-algorithm">Activate</a> algorithm.)</td>
        </tr>
        <tr>
          <td><dfn id="service-worker-global-scope-fetch-event"><code>fetch</code></dfn></td>
          <td><code><a href="#fetch-event-interface">FetchEvent</a></code></td>
          <td>[<a href="#dfn-functional-events">Functional event</a>] <a href="https://fetch.spec.whatwg.org/">Fetch</a> invokes <a href="#on-fetch-request-algorithm">Handle Fetch</a> with <var>request</var>. As a result of performing <a href="#on-fetch-request-algorithm">Handle Fetch</a>, the Service Woker returns a <a href="https://fetch.spec.whatwg.org/#concept-response">response</a> to <a href="https://fetch.spec.whatwg.org/">Fetch</a>. The <a href="https://fetch.spec.whatwg.org/#concept-response">response</a>, represented by a <code><a href="https://fetch.spec.whatwg.org/#response">Response</a></code> object, can be retrieved from a <a href="#cache-interface">Cache</a> object or directly from network using <code><a href="https://fetch.spec.whatwg.org/#dom-global-fetch">self.fetch(<var>input</var>, <var>init</var>)</a></code> method. (A custom <code><a href="https://fetch.spec.whatwg.org/#response">Response</a></code> object can be another option.)</td>
        </tr>
        <tr>
          <td><dfn id="service-worker-global-scope-message-event"><code>message</code></dfn></td>
          <td><code><a href="#extendablemessage-event-interface">ExtendableMessageEvent</a></code></td>
          <td>When it receives a message.</td>
        </tr>
      </tbody>
    </table>
  </section>
</section>

<section title="cache-objects"><header><span class="section-number">5</span> <h2 id="cache-objects" data-bookmark-label="5 Caches">Caches</h2><span class="anchor"><a style="text-decoration: none;" href="#cache-objects">¶</a></span></header>

  <p id="cache-objects.1">To allow authors to fully manage their content caches for offline use, the <a href="https://html.spec.whatwg.org/multipage/browsers.html#window">Window</a> and the <a href="https://html.spec.whatwg.org/multipage/workers.html#workerglobalscope">WorkerGlobalScope</a> provide the asynchronous caching methods that open and manipulate <code><a href="#cache-interface">Cache</a></code> objects. An <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a> can have multiple, named <code><a href="#cache-interface">Cache</a></code> objects, whose contents are entirely under the control of scripts. Caches are not shared across <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origins</a>, and they are completely isolated from the browser's HTTP cache.</p>

  <section title="cache-constructs"><header><span class="section-number">5.1</span> <h3 id="cache-constructs" data-bookmark-label="5.1 Constructs">Constructs</h3><span class="anchor"><a style="text-decoration: none;" href="#cache-constructs">¶</a></span></header>


    <p id="cache-constructs.1">A <dfn id="dfn-fetching-record">fetching record</dfn> is a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-list-and-record-specification-type">Record</a> {[[key]], [[value]]} where [[key]] is a <code><a href="https://fetch.spec.whatwg.org/#request">Request</a></code> and [[value]] is a <code><a href="https://fetch.spec.whatwg.org/#response">Response</a></code>.</p>
    <p id="cache-constructs.2">A <a href="#dfn-fetching-record">fetching record</a> has an associated <dfn id="dfn-incumbent-record">incumbent record</dfn> (a <a href="#dfn-fetching-record">fetching record</a>). It is initially set to null.</p>
    <p id="cache-constructs.3">A <dfn id="dfn-request-to-response-map">request to response map</dfn> is a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-list-and-record-specification-type">List</a> of <a href="#dfn-fetching-record">fetching records</a>.</p>

    <p id="cache-constructs.4">A <dfn id="dfn-name-to-cache-map">name to cache map</dfn> is a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-list-and-record-specification-type">List</a> of the <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-list-and-record-specification-type">Record</a> {[[key]], [[value]]} where [[key]] is a string that represents a name of the <code><a href="#cache-interface">Cache</a></code> object and [[value]] is a <code><a href="#cache-interface">Cache</a></code> object.</p>

    <p id="cache-constructs.5">Each <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a> has an associated <a href="#dfn-name-to-cache-map">name to cache map</a>.</p>
  </section>

  <section title="cache-lifetimes"><header><span class="section-number">5.2</span> <h3 id="cache-lifetimes" data-bookmark-label="5.2 Understanding Cache Lifetimes">Understanding Cache Lifetimes</h3><span class="anchor"><a style="text-decoration: none;" href="#cache-lifetimes">¶</a></span></header>


    <p id="cache-lifetimes.1">The <code><a href="#cache-interface">Cache</a></code> instances are not part of the browser's HTTP cache. The <code><a href="#cache-interface">Cache</a></code> objects are exactly what authors have to manage themselves. The <code><a href="#cache-interface">Cache</a></code> objects do not get updated unless authors explicitly request them to be. The <code><a href="#cache-interface">Cache</a></code> objects do not expire unless authors delete the entries. The <code><a href="#cache-interface">Cache</a></code> objects do not disappear just because the <a href="#dfn-service-worker">service worker</a> script is updated. That is, caches are not updated automatically. Updates must be manually managed. This implies that authors should version their caches by name and make sure to use the caches only from the version of the <a href="#dfn-service-worker">service worker</a> that can safely operate on.</p>
  </section>

  <section title="self-caches"><header><span class="section-number">5.3</span> <h3 id="self-caches" data-bookmark-label="5.3 self.caches"><code>self.caches</code></h3><span class="anchor"><a style="text-decoration: none;" href="#self-caches">¶</a></span></header>

<pre><code>partial interface <a href="https://html.spec.whatwg.org/multipage/browsers.html#window">Window</a> {
  [SameObject] readonly attribute <a href="#cache-storage-interface">CacheStorage</a> <a href="#global-caches-attribute">caches</a>;
};

partial interface <a href="https://html.spec.whatwg.org/multipage/workers.html#workerglobalscope">WorkerGlobalScope</a> {
  [SameObject] readonly attribute <a href="#cache-storage-interface">CacheStorage</a> <a href="#global-caches-attribute">caches</a>;
};
</code></pre>
    <section title="global-caches"><header><span class="section-number">5.3.1</span> <h4 id="global-caches" data-bookmark-label="5.3.1 caches"><code>caches</code></h4><span class="anchor"><a style="text-decoration: none;" href="#global-caches">¶</a></span></header>


      <p id="global-caches.1"><dfn id="global-caches-attribute"><code>caches</code></dfn> attribute <em class="rfc2119" title="MUST">must</em> return a <code><a href="#cache-storage-interface">CacheStorage</a></code> object that represents the <a href="#dfn-name-to-cache-map">name to cache map</a> of the <a href="https://dom.spec.whatwg.org/#context-object">context object</a>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#environment-settings-object">environment settings object</a>'s <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a>.</p>
    </section>
  </section>

  <section title="cache"><header><span class="section-number">5.4</span> <h3 id="cache" data-bookmark-label="5.4 Cache"><code>Cache</code></h3><span class="anchor"><a style="text-decoration: none;" href="#cache">¶</a></span></header>

<pre><code>[Exposed=(Window,Worker)]
interface <dfn id="cache-interface" title="Cache">Cache</dfn> {
  [NewObject] <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;<a href="https://fetch.spec.whatwg.org/#response">Response</a>&gt; <a href="#cache-match-method">match</a>(<a href="https://fetch.spec.whatwg.org/#requestinfo">RequestInfo</a> <var>request</var>, optional <a href="#cache-query-options-dictionary">CacheQueryOptions</a> <var>options</var>);
  [NewObject] <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;sequence&lt;<a href="https://fetch.spec.whatwg.org/#response">Response</a>&gt;&gt; <a href="#cache-matchall-method">matchAll</a>(optional <a href="https://fetch.spec.whatwg.org/#requestinfo">RequestInfo</a> <var>request</var>, optional <a href="#cache-query-options-dictionary">CacheQueryOptions</a> <var>options</var>);
  [NewObject] <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;void&gt; <a href="#cache-add-method">add</a>(<a href="https://fetch.spec.whatwg.org/#requestinfo">RequestInfo</a> <var>request</var>);
  [NewObject] <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;void&gt; <a href="#cache-addAll-method">addAll</a>(sequence&lt;<a href="https://fetch.spec.whatwg.org/#requestinfo">RequestInfo</a>&gt; <var>requests</var>);
  [NewObject] <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;void&gt; <a href="#cache-put-method">put</a>(<a href="https://fetch.spec.whatwg.org/#requestinfo">RequestInfo</a> <var>request</var>, <a href="https://fetch.spec.whatwg.org/#response">Response</a> <var>response</var>);
  [NewObject] <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;boolean&gt; <a href="#cache-delete-method">delete</a>(<a href="https://fetch.spec.whatwg.org/#requestinfo">RequestInfo</a> <var>request</var>, optional <a href="#cache-query-options-dictionary">CacheQueryOptions</a> <var>options</var>);
  [NewObject] <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;sequence&lt;<a href="https://fetch.spec.whatwg.org/#request">Request</a>&gt;&gt; <a href="#cache-keys-method">keys</a>(optional <a href="https://fetch.spec.whatwg.org/#requestinfo">RequestInfo</a> <var>request</var>, optional <a href="#cache-query-options-dictionary">CacheQueryOptions</a> <var>options</var>);
};

dictionary <dfn id="cache-query-options-dictionary" title="CacheQueryOptions">CacheQueryOptions</dfn> {
  boolean ignoreSearch = false;
  boolean ignoreMethod = false;
  boolean ignoreVary = false;
  DOMString cacheName;
};

dictionary <dfn id="cache-batch-operation-dictionary" title="CacheBatchOperation">CacheBatchOperation</dfn> {
  DOMString type;
  Request request;
  Response response;
  CacheQueryOptions options;
};
</code></pre>
    <p id="cache.1">A <code><a href="#cache-interface">Cache</a></code> object represents a <a href="#dfn-request-to-response-map">request to response map</a>. Multiple separate objects implementing the <code><a href="#cache-interface">Cache</a></code> interface across <a href="https://html.spec.whatwg.org/multipage/webappapis.html#document-environment">document environments</a> and <a href="https://html.spec.whatwg.org/multipage/webappapis.html#worker-environment">worker environments</a> can all be associated with the same <a href="#dfn-request-to-response-map">request to response map</a> simultaneously.</p>

    <p id="cache.2"><code><a href="#cache-interface">Cache</a></code> objects are always enumerable via <code><a href="#global-caches-attribute">self.caches</a></code> in insertion order (per <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-map-objects">ECMAScript 6 Map objects</a>.)</p>

    <section title="cache-match"><header><span class="section-number">5.4.1</span> <h4 id="cache-match" data-bookmark-label="5.4.1 match(request, options)"><code>match(<var>request</var>, <var>options</var>)</code></h4><span class="anchor"><a style="text-decoration: none;" href="#cache-match">¶</a></span></header>


      <p id="cache-match.1"><dfn id="cache-match-method"><code>match(<var>request</var>, <var>options</var>)</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>

      <div class="algorithm">
      <ol>
        <li>Let <var>promise</var> be a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a>.</li>
        <li>Run these steps in parallel:
          <ol>
            <li>Let <var>p</var> be the result of running the algorithm specified in <code><a href="#cache-matchall-method">matchAll(<var>request</var>, <var>options</var>)</a></code> method with <var>request</var> and <var>options</var> as the arguments.</li>
            <li>Wait until <var>p</var> settles.</li>
            <li>If <var>p</var> rejects with an exception, then:
              <ol>
                <li>Reject <var>promise</var> with that exception.</li>
              </ol>
            </li>
            <li>Else if <var>p</var> resolves with an array, <var>responseArray</var>, then:
              <ol>
                <li>If <var>responseArray</var> is an empty array, then:
                  <ol>
                    <li>Resolve <var>promise</var> with undefined.</li>
                  </ol>
                </li>
                <li>Else:
                  <ol>
                    <li>Resolve <var>promise</var> with the first element of <var>responseArray</var>.</li>
                  </ol>
                </li>
              </ol>
            </li>
          </ol>
        </li>
        <li>Return <var>promise</var>.</li>
      </ol>
      </div>
    </section>

    <section title="cache-matchall"><header><span class="section-number">5.4.2</span> <h4 id="cache-matchall" data-bookmark-label="5.4.2 matchAll(request, options)"><code>matchAll(<var>request</var>, <var>options</var>)</code></h4><span class="anchor"><a style="text-decoration: none;" href="#cache-matchall">¶</a></span></header>


      <p id="cache-matchall.1"><dfn id="cache-matchall-method"><code>matchAll(<var>request</var>, <var>options</var>)</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>

      <div class="algorithm">
      <ol>
        <li>Let <var>promise</var> be a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a>.</li>
        <li>Run these steps in parallel:
          <ol>
            <li>Let <var>responseArray</var> be an empty array.</li>
            <li>If the optional argument <var>request</var> is omitted, then:
              <ol>
                <li>For each <a href="#dfn-fetching-record">fetching record</a> <var>entry</var> of its <a href="#dfn-request-to-response-map">request to response map</a>, in key insertion order:
                  <ol>
                    <li>Add a  copy of <var>entry</var>.[[value]] to <var>responseArray</var>.</li>
                  </ol>
                </li>
                <li>Resolve <var>promise</var> with <var>responseArray</var>.</li>
                <li>Abort these steps.</li>
              </ol>
            </li>
            <li>Else:
              <ol>
                <li>Let <var>r</var> be null.</li>
                <li>If <var>request</var> is a <a href="https://fetch.spec.whatwg.org/#dom-request">Request</a> object, then:
                  <ol>
                    <li>Set <var>r</var> to <var>request</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-request">request</a>.</li>
                    <li>If <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-method">method</a> is neither `<code>GET</code>` nor `<code>HEAD</code>` and <var>options</var>.<var>ignoreMethod</var> is false, resolve <var>promise</var> with an empty array.</li>
                  </ol>
                </li>
                <li>Else if <var>request</var> is a string, then:
                  <ol>
                    <li>Set <var>r</var> to the associated <a href="https://fetch.spec.whatwg.org/#concept-request">request</a> of the result of invoking the initial value of <a href="https://fetch.spec.whatwg.org/#dom-request">Request</a> as constructor with <var>request</var> as its argument. If this <a href="http://heycam.github.io/webidl/#dfn-throw">throws</a> an exception, return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with that exception.</li>
                  </ol>
                </li>
                <li>Set <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-url">url</a>'s <a href="https://url.spec.whatwg.org/#concept-url-fragment">fragment</a> to null.</li>
                <li>Let <var>entries</var> be the result of running <a href="#query-cache-algorithm">Query Cache</a> algorithm passing a <a href="https://fetch.spec.whatwg.org/#request">Request</a> object associated with <var>r</var> and <var>options</var> as the arguments.</li>
                <li>For each <var>entry</var> of <var>entries</var>:
                  <ol>
                    <li>Let <var>response</var> be null.</li>
                    <li>If the <a href="#dfn-incumbent-record">incumbent record</a> <var>incumbentRecord</var> of the corresponding <a href="#dfn-fetching-record">fetching record</a> <var>fetchingRecord</var> in <a href="#dfn-request-to-response-map">request to response map</a> is not null, set <var>response</var> to a copy of <var>incumbentRecord</var>.[[value]].</li>
                    <li>Else, set <var>response</var> to a copy of <var>entry</var>[1].</li>
                    <li>If <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#concept-method">method</a> is `<code>HEAD</code>` and <var>options</var>.<var>ignoreMethod</var> is false, set <var>response</var>'s <a href="https://fetch.spec.whatwg.org/#concept-body-body">body</a> to null.</li>
                    <li>Add <var>response</var> to <var>responseArray</var>.</li>
                  </ol>
                </li>
                <li>Resolve <var>promise</var> with <var>responseArray</var>.</li>
              </ol>
            </li>
          </ol>
        </li>
        <li>Return <var>promise</var>.</li>
      </ol>
      </div>
    </section>

    <section title="cache-add"><header><span class="section-number">5.4.3</span> <h4 id="cache-add" data-bookmark-label="5.4.3 add(request)"><code>add(<var>request</var>)</code></h4><span class="anchor"><a style="text-decoration: none;" href="#cache-add">¶</a></span></header>


      <p id="cache-add.1"><dfn id="cache-add-method"><code>add(<var>request</var>)</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>

      <div class="algorithm">
      <ol>
        <li>Let <var>requests</var> be an array containing only <var>request</var>.</li>
        <li>Set <var>responseArrayPromise</var> to the result of running the algorithm specified in <code><a href="#cache-addAll-method">addAll(<var>requests</var>)</a></code> passing <var>requests</var> as the argument.</li>
        <li>Return the result of <a href="http://www.w3.org/2001/tag/doc/promises-guide#transforming-by">transforming</a> <var>responseArrayPromise</var> with a fulfillment handler that returns undefined.</li>
      </ol>
      </div>
    </section>

    <section title="cache-addAll"><header><span class="section-number">5.4.4</span> <h4 id="cache-addAll" data-bookmark-label="5.4.4 addAll(requests)"><code>addAll(<var>requests</var>)</code></h4><span class="anchor"><a style="text-decoration: none;" href="#cache-addAll">¶</a></span></header>


      <p id="cache-addAll.1"><dfn id="cache-addAll-method"><code>addAll(<var>requests</var>)</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>

      <div class="algorithm">
      <ol>
        <li>Let <var>responsePromiseArray</var> be an empty array.</li>
        <li>Let <var>requestArray</var> be an empty array.</li>
        <li>For each <var>request</var> whose type is <a href="https://fetch.spec.whatwg.org/#request">Request</a> in <var>requests</var>:
          <ol>
            <li>Let <var>r</var> be <var>request</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-request">request</a>.</li>
            <li>If <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-url">url</a>'s <a href="https://url.spec.whatwg.org/#concept-url-scheme">scheme</a> is not one of "<code>http</code>" and "<code>https</code>", or <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-method">method</a> is not `<code>GET</code>`, return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with a <code>TypeError</code>.</li>
          </ol>
        </li>
        <li>For each <var>request</var> in <var>requests</var>:
          <ol>
            <li>Let <var>r</var> be the associated <a href="https://fetch.spec.whatwg.org/#concept-request-request">request</a> of the result of invoking the initial value of <a href="https://fetch.spec.whatwg.org/#dom-request">Request</a> as constructor with <var>request</var> as its argument. If this <a href="http://heycam.github.io/webidl/#dfn-throw">throws</a> an exception, return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with that exception.</li>
            <li>If <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-url">url</a>'s <a href="https://url.spec.whatwg.org/#concept-url-scheme">scheme</a> is not one of "<code>http</code>" and "<code>https</code>", then:
              <ol>
                <li><a href="https://fetch.spec.whatwg.org/#concept-fetch-terminate">Terminate</a> all the ongoing <a href="https://fetch.spec.whatwg.org/#concept-fetch">fetches</a> initiated by <var>requests</var> with reason <em>fatal</em>.</li>
                <li>Break the loop.</li>
              </ol>
            </li>
            <li>Set <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-url">url</a>'s <a href="https://url.spec.whatwg.org/#concept-url-fragment">fragment</a> to null.</li>
            <li>Set <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-context">context</a> to "<code>fetch</code>".</li>
            <li>Add a <a href="https://fetch.spec.whatwg.org/#request">Request</a> object associated with <var>r</var> to <var>requestArray</var>.</li>
            <li>Let <var>responsePromise</var> be a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a>.</li>
            <li>Run the following in parallel:
              <ul>
                <li><a href="https://fetch.spec.whatwg.org/#concept-fetch">Fetch</a> <var>r</var>.</li>
                <li>To <a href="https://fetch.spec.whatwg.org/#process-response">process response</a> for <var>response</var>, run these substeps:
                  <ol>
                    <li>If <var>response</var>'s <a href="https://fetch.spec.whatwg.org/#concept-response-type">type</a> is <em>error</em>, reject <var>responsePromise</var> with a <code>TypeError</code>.</li>
                    <li>Else if <var>response</var>'s <a href="https://fetch.spec.whatwg.org/#concept-response-header-list">header list</a> contains a <a href="https://fetch.spec.whatwg.org/#concept-header">header</a> <a href="https://fetch.spec.whatwg.org/#concept-header-name">named</a> `<code>Vary</code>`, then:
                      <ol>
                        <li>Let <var>varyHeaders</var> be the array containing the elements corresponding to the <a href="https://tools.ietf.org/html/rfc7230#section-3.2">field-values</a> of the <a href="https://tools.ietf.org/html/rfc7231#section-7.1.4">Vary</a> header.</li>
                        <li>Let <var>matchAsterisk</var> be false.</li>
                        <li>For each <var>f</var> in <var>varyHeaders</var>:
                          <ol>
                            <li>If <var>f</var> matches "<code>*</code>", set <var>matchAsterisk</var> to true and break the loop.</li>
                          </ol>
                        </li>
                        <li>If <var>matchAsterisk</var> is true, reject <var>responsePromise</var> with a <code>TypeError</code>.</li>
                        <li>Else, resolve <var>responsePromise</var> with a new <a href="https://fetch.spec.whatwg.org/#response">Response</a> object associated with <var>response</var>.</li>
                      </ol>
                    </li>
                    <li>Else, resolve <var>responsePromise</var> with a new <a href="https://fetch.spec.whatwg.org/#response">Response</a> object associated with <var>response</var>.</li>
                  </ol>
                  <p class="note">This step ensures that the promise for this fetch resolves as soon as the response's headers become available.</p>
                </li>
                <li>To <a href="https://fetch.spec.whatwg.org/#process-response-body">process response body</a> for <var>response</var>, do nothing.</li>
                <li>To <a href="https://fetch.spec.whatwg.org/#process-response-end-of-file">process response end-of-file</a> for <var>response</var>, do nothing.</li>
              </ul>
            </li>
            <li>Add <var>responsePromise</var> to <var>responsePromiseArray</var>.</li>
          </ol>
        </li>
        <li>Let <var>p</var> be <a href="http://www.w3.org/2001/tag/doc/promises-guide#waiting-for-all">waiting for all of <var>responsePromiseArray</var></a>.</li>
        <li>Return the result of <a href="http://www.w3.org/2001/tag/doc/promises-guide#transforming-by">transforming</a> <var>p</var> with a fulfillment handler that, when called with argument <var>responseArray</var>, performs the following substeps in parallel:
          <ol>
            <li>Let <var>operations</var> be an empty array.</li>
            <li>For each <var>response</var> in <var>responseArray</var> with the index <var>index</var>:
              <ol>
                <li>If <var>response</var>'s <a href="https://fetch.spec.whatwg.org/#concept-body-body">body</a> is non-null, then:
                <ol>
                  <li>If <var>response</var>'s <a href="https://fetch.spec.whatwg.org/#concept-body-used-flag">used flag</a> is set, <a href="http://heycam.github.io/webidl/#dfn-throw">throw</a> a <code>TypeError</code>.</li>
                  <li>Set <var>response</var>'s <a href="https://fetch.spec.whatwg.org/#concept-body-used-flag">used flag</a>.</li>
                </ol>
              </li>
                <li>Let <var>o</var> be an empty object representing a <code><a href="#cache-batch-operation-dictionary">CacheBatchOperation</a></code> dictionary.</li>
                <li>Set the <var>type</var> dictionary member of <var>o</var> to "put".</li>
                <li>Set the <var>request</var> dictionary member of <var>o</var> to <var>requestArray</var>[<var>index</var>].</li>
                <li>Set the <var>response</var> dictionary member of <var>o</var> to <var>response</var>.</li>
                <li>Add <var>o</var> to <var>operations</var>.</li>
              </ol>
            </li>
            <li>Let <var>resultPromise</var> to the result of running <a href="#batch-cache-operations-algorithm">Batch Cache Operations</a> algorithm passing <var>operations</var> as the argument.</li>
            <li>Return the result of <a href="http://www.w3.org/2001/tag/doc/promises-guide#transforming-by">transforming</a> <var>resultPromise</var>  with a fulfillment handler that, when called with argument <var>responses</var>, performs the following substeps in parallel:
              <ol>
                <li>Let <var>responseBodyPromiseArray</var> be an empty array.</li>
                <li>For each <var>response</var> in <var>responses</var>:
                  <ol>
                    <li>Let <var>responseBodyPromise</var> be a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a>.</li>
                    <li>Run the following substeps in parallel:
                      <ol>
                        <li>Wait for either end-of-file to have been pushed to <var>response</var>'s associated <a href="https://fetch.spec.whatwg.org/#concept-response-response">response</a> <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#concept-response-body">body</a> or for <var>r</var> to have a <a href="https://fetch.spec.whatwg.org/#concept-response-termination-reason">termination reason</a>.</li>
                        <li>If <var>r</var> had a <a href="https://fetch.spec.whatwg.org/#concept-response-termination-reason">termination reason</a>, then:
                          <ol>
                            <li>If the <a href="#dfn-incumbent-record">incumbent record</a> <var>incumbentRecord</var> of the corresponding <a href="#dfn-fetching-record">fetching record</a> <var>fetchingRecord</var> in <a href="#dfn-request-to-response-map">request to response map</a> is not null, then:
                              <ol>
                                <li>Set <var>fetchingRecord</var> in <a href="#dfn-request-to-response-map">request to response map</a> to the copy of <var>incumbentRecord</var>.</li>
                              </ol>
                            </li>
                            <li>Else:
                              <ol>
                                <li>Delete <var>fetchingRecord</var> from <a href="#dfn-request-to-response-map">request to response map</a>.</li>
                              </ol>
                            </li>
                            <li>Reject <var>responseBodyPromise</var> with a <code>TypeError</code>.</li>
                          </ol>
                        </li>
                        <li>Else:
                          <ol>
                            <li>Set the <a href="#dfn-incumbent-record">incumbent record</a> of the corresponding <a href="#dfn-fetching-record">fetching record</a> <var>fetchingRecord</var> in <a href="#dfn-request-to-response-map">request to response map</a> to the copy of <var>fetchingRecord</var>.</li>
                            <li>Let <var>invalidRecords</var> be the result of running <a href="#query-cache-algorithm">Query Cache</a> algorithm passing <var>fetchingRecord</var>.[[key]] as the argument.</li>
                            <li>For each <var>invalidRecord</var> in <var>invalidRecords</var>:
                              <ol>
                                <li>If <var>invalidRecord</var> is not <var>fetchingRecord</var>, delete it from <a href="#dfn-request-to-response-map">request to response map</a>.</li>
                              </ol>
                            </li>
                            <li>Resolve <var>responseBodyPromise</var> with <var>response</var>.</li>
                          </ol>
                        </li>
                      </ol>
                    </li>
                    <li>Add <var>responseBodyPromise</var> to <var>responseBodyPromiseArray</var>.</li>
                  </ol>
                </li>
                <li>Let <var>q</var> be <a href="http://www.w3.org/2001/tag/doc/promises-guide#waiting-for-all">waiting for all of</a> <var>responseBodyPromiseArray</var>.</li>
                <li>Return the result of <a href="http://www.w3.org/2001/tag/doc/promises-guide#transforming-by">transforming</a> <var>q</var>  with a fulfillment handler that returns undefined.</li>
              </ol>
            </li>
          </ol>
        </li>
      </ol>
      </div>
    </section>

    <section title="cache-put"><header><span class="section-number">5.4.5</span> <h4 id="cache-put" data-bookmark-label="5.4.5 put(request, response)"><code>put(<var>request</var>, <var>response</var>)</code></h4><span class="anchor"><a style="text-decoration: none;" href="#cache-put">¶</a></span></header>


      <p id="cache-put.1"><dfn id="cache-put-method"><code>put(<var>request</var>, <var>response</var>)</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>

      <div class="algorithm">
      <ol>
        <li>Let <var>r</var> be null.</li>
        <li>If <var>request</var> is a <a href="https://fetch.spec.whatwg.org/#dom-request">Request</a> object, then:
          <ol>
            <li>Set <var>r</var> to <var>request</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-request">request</a>.</li>
            <li>If <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-url">url</a>'s <a href="https://url.spec.whatwg.org/#concept-url-scheme">scheme</a> is not one of "<code>http</code>" and "<code>https</code>", or <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-method">method</a> is not `<code>GET</code>`, return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with a <code>TypeError</code>.</li>
          </ol>
        </li>
        <li>Else if <var>request</var> is a string, then:
          <ol>
            <li>Set <var>r</var> to the associated <a href="https://fetch.spec.whatwg.org/#concept-request">request</a> of the result of invoking the initial value of <a href="https://fetch.spec.whatwg.org/#dom-request">Request</a> as constructor with <var>request</var> as its argument. If this <a href="http://heycam.github.io/webidl/#dfn-throw">throws</a> an exception, return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with that exception.</li>
            <li>If <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-url">url</a>'s <a href="https://url.spec.whatwg.org/#concept-url-scheme">scheme</a> is not one of "<code>http</code>" and "<code>https</code>", return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with a <code>TypeError</code>.</li>
          </ol>
        </li>
        <li>Set <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-url">url</a>'s <a href="https://url.spec.whatwg.org/#concept-url-fragment">fragment</a> to null.</li>
        <li>If <var>response</var>'s associated <a href="https://fetch.spec.whatwg.org/#concept-response-response">response</a>'s <a href="https://fetch.spec.whatwg.org/#concept-response-header-list">header list</a> contains a <a href="https://fetch.spec.whatwg.org/#concept-header">header</a> <a href="https://fetch.spec.whatwg.org/#concept-header-name">named</a> `<code>Vary</code>`, then:
          <ol>
            <li>Let <var>varyHeaders</var> be the array containing the elements corresponding to the <a href="https://tools.ietf.org/html/rfc7230#section-3.2">field-values</a> of the <a href="https://tools.ietf.org/html/rfc7231#section-7.1.4">Vary</a> header.</li>
            <li>For each <var>f</var> in <var>varyHeaders</var>:
              <ol>
                <li>If <var>f</var> matches "<code>*</code>", return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with a <code>TypeError</code>.</li>
              </ol>
            </li>
          </ol>
        </li>
        <li>If <var>response</var>'s <a href="https://fetch.spec.whatwg.org/#concept-body-body">body</a> is non-null, then:
          <ol>
            <li>If <var>response</var>'s <a href="https://fetch.spec.whatwg.org/#concept-body-used-flag">used flag</a> is set, return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with a <code>TypeError</code>.</li>
            <li>Set <var>response</var>'s <a href="https://fetch.spec.whatwg.org/#concept-body-used-flag">used flag</a>.</li>
          </ol>
        </li>
        <li>Let <var>operations</var> be an empty array.</li>
        <li>Let <var>o</var> be an empty object representing a <code><a href="#cache-batch-operation-dictionary">CacheBatchOperation</a></code> dictionary.</li>
        <li>Set the <var>type</var> dictionary member of <var>o</var> to "put".</li>
        <li>Set the <var>request</var> dictionary member of <var>o</var> to a <a href="https://fetch.spec.whatwg.org/#request">Request</a> object associated with <var>r</var>.</li>
        <li>Set the <var>response</var> dictionary member of <var>o</var> to <var>response</var>.</li>
        <li>Add <var>o</var> to <var>operations</var>.</li>
        <li>Let <var>resultPromise</var> to the result of running <a href="#batch-cache-operations-algorithm">Batch Cache Operations</a> passing <var>operations</var> as the argument.</li>
        <li>Return the result of <a href="http://www.w3.org/2001/tag/doc/promises-guide#transforming-by">transforming</a> <var>resultPromise</var> with a fulfillment handler that, when called with argument <var>responses</var>, performs the following substeps in parallel:
          <ol>
            <li>Wait for either end-of-file to have been pushed to <var>responses</var>[0]'s associated <a href="https://fetch.spec.whatwg.org/#concept-response-response">response</a> <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#concept-response-body">body</a> or for <var>r</var> to have a <a href="https://fetch.spec.whatwg.org/#concept-response-termination-reason">termination reason</a>.</li>
            <li>If <var>r</var> had a <a href="https://fetch.spec.whatwg.org/#concept-response-termination-reason">termination reason</a>, then:
              <ol>
                <li>If the <a href="#dfn-incumbent-record">incumbent record</a> <var>incumbentRecord</var> of the corresponding <a href="#dfn-fetching-record">fetching record</a> <var>fetchingRecord</var> in <a href="#dfn-request-to-response-map">request to response map</a> is not null, then:
                  <ol>
                    <li>Set <var>fetchingRecord</var> in <a href="#dfn-request-to-response-map">request to response map</a> to the copy of <var>incumbentRecord</var>.</li>
                  </ol>
                </li>
                <li>Else:
                  <ol>
                    <li>Delete <var>fetchingRecord</var> from <a href="#dfn-request-to-response-map">request to response map</a>.</li>
                  </ol>
                </li>
                <li><a href="http://heycam.github.io/webidl/#dfn-throw">Throw</a> a <code>TypeError</code>.</li>
              </ol>
            </li>
            <li>Else:
              <ol>
                <li>Set the <a href="#dfn-incumbent-record">incumbent record</a> of the corresponding <a href="#dfn-fetching-record">fetching record</a> <var>fetchingRecord</var> in <a href="#dfn-request-to-response-map">request to response map</a> to the copy of <var>fetchingRecord</var>.</li>
                <li>Let <var>invalidRecords</var> be the result of running <a href="#query-cache-algorithm">Query Cache</a> algorithm passing <var>fetchingRecord</var>.[[key]] as the argument.</li>
                <li>For each <var>invalidRecord</var> in <var>invalidRecords</var>:
                  <ol>
                    <li>If <var>invalidRecord</var> is not <var>fetchingRecord</var>, delete it from <a href="#dfn-request-to-response-map">request to response map</a>.</li>
                  </ol>
                </li>
                <li>Return undefined.</li>
              </ol>
            </li>
          </ol>
        </li>
      </ol>
      </div>
    </section>

    <section title="cache-delete"><header><span class="section-number">5.4.6</span> <h4 id="cache-delete" data-bookmark-label="5.4.6 delete(request, options)"><code>delete(<var>request</var>, <var>options</var>)</code></h4><span class="anchor"><a style="text-decoration: none;" href="#cache-delete">¶</a></span></header>


      <p id="cache-delete.1"><dfn id="cache-delete-method"><code>delete(<var>request</var>, <var>options</var>)</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>

      <div class="algorithm">
      <ol>
        <li>Let <var>r</var> be null.</li>
        <li>If <var>request</var> is a <a href="https://fetch.spec.whatwg.org/#dom-request">Request</a> object, then:
          <ol>
            <li>Set <var>r</var> to <var>request</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-request">request</a>.</li>
            <li>If <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-method">method</a> is neither `<code>GET</code>` nor `<code>HEAD</code>` and <var>options</var>.<var>ignoreMethod</var> is false, return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> resolved with false.</li>
          </ol>
        </li>
        <li>Else if <var>request</var> is a string, then:
          <ol>
            <li>Set <var>r</var> to the associated <a href="https://fetch.spec.whatwg.org/#concept-request">request</a> of the result of invoking the initial value of <a href="https://fetch.spec.whatwg.org/#dom-request">Request</a> as constructor with <var>request</var> as its argument. If this <a href="http://heycam.github.io/webidl/#dfn-throw">throws</a> an exception, return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with that exception.</li>
          </ol>
        </li>
        <li>Set <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-url">url</a>'s <a href="https://url.spec.whatwg.org/#concept-url-fragment">fragment</a> to null.</li>
        <li>Let <var>operations</var> be an empty array.</li>
        <li>Let <var>o</var> be an empty object representing a <code><a href="#cache-batch-operation-dictionary">CacheBatchOperation</a></code> dictionary.</li>
        <li>Set the <var>type</var> dictionary member of <var>o</var> to "delete".</li>
        <li>Set the <var>request</var> dictionary member of <var>o</var> to a <a href="https://fetch.spec.whatwg.org/#request">Request</a> object associated with <var>r</var>.</li>
        <li>Set the <var>options</var> dictionary member of <var>o</var> to <var>options</var>.</li>
        <li>Add <var>o</var> to <var>operations</var>.</li>
        <li>Let <var>resultPromise</var> to the result of running <a href="#batch-cache-operations-algorithm">Batch Cache Operations</a> passing <var>operations</var> as the argument.</li>
        <li>Return the result of <a href="http://www.w3.org/2001/tag/doc/promises-guide#transforming-by">transforming</a> <var>resultPromise</var> with a fulfillment handler, when called with argument <var>responseArray</var>, performs the following substeps in parallel:
          <ol>
            <li>If <var>responseArray</var> is not null, return true.</li>
            <li>Else, return false.</li>
          </ol>
        </li>
      </ol>
      </div>
    </section>

    <section title="cache-keys"><header><span class="section-number">5.4.7</span> <h4 id="cache-keys" data-bookmark-label="5.4.7 keys(request, options)"><code>keys(<var>request</var>, <var>options</var>)</code></h4><span class="anchor"><a style="text-decoration: none;" href="#cache-keys">¶</a></span></header>


      <p id="cache-keys.1"><dfn id="cache-keys-method"><code>keys(<var>request</var>, <var>options</var>)</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>

      <div class="algorithm">
      <ol>
        <li>Let <var>promise</var> be a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a>.</li>
        <li>Run these steps in parallel:
          <ol>
            <li>Let <var>resultArray</var> be an empty array.</li>
            <li>If the optional argument <var>request</var> is omitted, then:
              <ol>
                <li>For each <a href="#dfn-fetching-record">fetching record</a> <var>entry</var> of its <a href="#dfn-request-to-response-map">request to response map</a>, in key insertion order:
                  <ol>
                    <li>Add <var>entry</var>.[[key]] to <var>resultArray</var>.</li>
                  </ol>
                </li>
              </ol>
            </li>
            <li>Else:
              <ol>
                <li>Let <var>r</var> be null.</li>
                <li>If <var>request</var> is a <a href="https://fetch.spec.whatwg.org/#dom-request">Request</a> object, then:
                  <ol>
                    <li>Set <var>r</var> to <var>request</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-request">request</a>.</li>
                    <li>If <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-method">method</a> is neither `<code>GET</code>` nor `<code>HEAD</code>` and <var>options</var>.<var>ignoreMethod</var> is false, resolve <var>promise</var> with an empty array.</li>
                  </ol>
                </li>
                <li>Else if <var>request</var> is a string, then:
                  <ol>
                    <li>Set <var>r</var> to the associated <a href="https://fetch.spec.whatwg.org/#concept-request">request</a> of the result of invoking the initial value of <a href="https://fetch.spec.whatwg.org/#dom-request">Request</a> as constructor with <var>request</var> as its argument. If this <a href="http://heycam.github.io/webidl/#dfn-throw">throws</a> an exception, return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with that exception.</li>
                  </ol>
                </li>
                <li>Set <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-url">url</a>'s <a href="https://url.spec.whatwg.org/#concept-url-fragment">fragment</a> to null.</li>
                <li>Let <var>requestResponseArray</var> be the result of running <a href="#query-cache-algorithm">Query Cache</a> algorithm passing a <a href="https://fetch.spec.whatwg.org/#request">Request</a> object that represents <var>r</var> and <var>options</var> as the arguments.</li>
                <li>For each <var>requestResponse</var> in <var>requestResponseArray</var>:
                  <ol>
                    <li>Add <var>requestResponse</var>[0] to <var>resultArray</var>.</li>
                  </ol>
                </li>
              </ol>
            </li>
            <li>Resolve <var>promise</var> with <var>resultArray</var>.</li>
          </ol>
        </li>
        <li>Return <var>promise</var>.</li>
      </ol>
      </div>
    </section>
  </section>

  <section title="cache-storage"><header><span class="section-number">5.5</span> <h3 id="cache-storage" data-bookmark-label="5.5 CacheStorage"><code>CacheStorage</code></h3><span class="anchor"><a style="text-decoration: none;" href="#cache-storage">¶</a></span></header>


<pre><code>[Exposed=(Window,Worker)]
interface <dfn id="cache-storage-interface" title="CacheStorage">CacheStorage</dfn> {
  [NewObject] <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;<a href="https://fetch.spec.whatwg.org/#response">Response</a>&gt; <a href="#cache-storage-match-method">match</a>(<a href="https://fetch.spec.whatwg.org/#requestinfo">RequestInfo</a> <var>request</var>, optional <a href="#cache-query-options-dictionary">CacheQueryOptions</a> <var>options</var>);
  [NewObject] <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;boolean&gt; <a href="#cache-storage-has-method">has</a>(DOMString <var>cacheName</var>);
  [NewObject] <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;<a href="#cache-interface">Cache</a>&gt; <a href="#cache-storage-open-method">open</a>(DOMString <var>cacheName</var>);
  [NewObject] <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;boolean&gt; <a href="#cache-storage-delete-method">delete</a>(DOMString <var>cacheName</var>);
  [NewObject] <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;sequence&lt;DOMString&gt;&gt; <a href="#cache-storage-keys-method">keys</a>();
};</code></pre>
<!--FIXME(jungkees): set method is not entirely dropped yet. <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">Promise</a>&lt;any&gt; set(DOMString <var>key</var>, <a href="#cache-interface">Cache</a> <var>val</var>);-->

    <p class="note" id="cache-storage.1"><a href="#cache-storage-interface">CacheStorage</a> interface is designed to largely conform to <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-map-objects">ECMAScript 6 Map objects</a> but entirely async, and with additional convenience methods. The methods, <code>clear</code>, <code>forEach</code>, <code>entries</code> and <code>values</code>, are intentionally excluded from the scope of the first version resorting to the ongoing discussion about the async iteration by TC39.</p>

    <p id="cache-storage.2">A <code><a href="#cache-storage-interface">CacheStorage</a></code> object represents a <a href="#dfn-name-to-cache-map">name to cache map</a>. Multiple separate objects implementing the <code><a href="#cache-storage-interface">CacheStorage</a></code> interface across <a href="https://html.spec.whatwg.org/multipage/webappapis.html#document-environment">document environments</a> and <a href="https://html.spec.whatwg.org/multipage/webappapis.html#worker-environment">worker environments</a> can all be associated with the same <a href="#dfn-name-to-cache-map">name to cache map</a> simultaneously.</p>

    <section title="cache-storage-match"><header><span class="section-number">5.5.1</span> <h4 id="cache-storage-match" data-bookmark-label="5.5.1 match(request, options)"><code>match(<var>request</var>, <var>options</var>)</code></h4><span class="anchor"><a style="text-decoration: none;" href="#cache-storage-match">¶</a></span></header>


      <p id="cache-storage-match.1"><dfn id="cache-storage-match-method"><code>match(<var>request</var>, <var>options</var>)</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>

      <div class="algorithm">
      <ol>
        <li>If the result of running <a href="https://w3c.github.io/webappsec/specs/powerfulfeatures/#settings-secure">is settings object a secure context</a> with the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#incumbent-settings-object">incumbent settings object</a> is <code>Not Secure</code>, return a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with a "<code><a href="http://heycam.github.io/webidl/#securityerror">SecurityError</a></code>" exception.</li>
        <li>Let <var>cacheName</var> be null.</li>
        <li>If the optional argument <var>options</var> is not omitted, then:
          <ol>
            <li>Set <var>cacheName</var> to <var>options</var>.<var>cacheName</var>.</li>
          </ol>
        </li>
        <li>If <var>cacheName</var> is not null, then:
          <ol>
            <li>Return a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> <var>p</var> and run the following substeps in parallel:
              <ol>
                <li>For each <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-list-and-record-specification-type">Record</a> {[[key]], [[value]]} <var>entry</var> of its <a href="#dfn-name-to-cache-map">name to cache map</a>, in key insertion order:
                  <ol>
                    <li>If <var>cacheName</var> matches <var>entry</var>.[[key]], then:
                      <ol>
                        <li>Resolve <var>p</var> with the result of running the algorithm specified in <code><a href="#cache-match-method">match(<var>request</var>, <var>options</var>)</a></code> method of <code><a href="#cache-interface">Cache</a></code> interface with <var>request</var> and <var>options</var> as the arguments (providing <var>entry</var>.[[value]] as thisArgument to the <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-ecmascript-function-objects-call-thisargument-argumentslist">[[Call]]</a> internal method of <code><a href="#cache-match-method">match(<var>request</var>, <var>options</var>)</a></code>.)</li>
                        <li>Abort these steps.</li>
                      </ol>
                    </li>
                  </ol>
                </li>
                <li>Reject <var>p</var> with a "<code><a href="http://heycam.github.io/webidl/#notfounderror">NotFoundError</a></code>" exception.</li>
              </ol>
            </li>
          </ol>
        </li>
        <li>Else:
          <ol>
            <li>Let <var>p</var> be a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> resolved with undefined.</li>
            <li>For each <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-list-and-record-specification-type">Record</a> {[[key]], [[value]]} <var>entry</var> of its <a href="#dfn-name-to-cache-map">name to cache map</a>, in key insertion order:
              <ol>
                <li>Set <var>p</var> to the result of <a href="http://www.w3.org/2001/tag/doc/promises-guide#transforming-by">transforming</a> itself with a fulfillment handler that, when called with argument <var>v</var>, performs the following substeps in parallel:
                  <ol>
                    <li>If <var>v</var> is not undefined, return <var>v</var>.</li>
                    <li>Return the result of running the algorithm specified in <code><a href="#cache-match-method">match(<var>request</var>, <var>options</var>)</a></code> method of <code><a href="#cache-interface">Cache</a></code> interface with <var>request</var> and <var>options</var> as the arguments (providing <var>entry</var>.[[value]] as thisArgument to the <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-ecmascript-function-objects-call-thisargument-argumentslist">[[Call]]</a> internal method of <code><a href="#cache-match-method">match(<var>request</var>, <var>options</var>)</a></code>.)</li>
                  </ol>
                </li>
              </ol>
            </li>
            <li>Return <var>p</var>.</li>
          </ol>
        </li>
      </ol>
      </div>
    </section>

    <section title="cache-storage-has"><header><span class="section-number">5.5.2</span> <h4 id="cache-storage-has" data-bookmark-label="5.5.2 has(cacheName)"><code>has(<var>cacheName</var>)</code></h4><span class="anchor"><a style="text-decoration: none;" href="#cache-storage-has">¶</a></span></header>


      <p id="cache-storage-has.1"><dfn id="cache-storage-has-method"><code>has(<var>cacheName</var>)</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>

      <div class="algorithm">
      <ol>
        <li>If the result of running <a href="https://w3c.github.io/webappsec/specs/powerfulfeatures/#settings-secure">is settings object a secure context</a> with the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#incumbent-settings-object">incumbent settings object</a> is <code>Not Secure</code>, return a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with a "<code><a href="http://heycam.github.io/webidl/#securityerror">SecurityError</a></code>" exception.</li>
        <li>Return a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> <var>p</var> resolved with the result of running the following substeps:
          <ol>
            <li>For each <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-list-and-record-specification-type">Record</a> {[[key]], [[value]]} <var>entry</var> of its <a href="#dfn-name-to-cache-map">name to cache map</a>, in key insertion order:
              <ol>
                <li>If <var>cacheName</var> matches <var>entry</var>.[[key]], then:
                  <ol>
                    <li>Return true.</li>
                  </ol>
                </li>
              </ol>
            </li>
            <li>Return false.</li>
          </ol>
        </li>
      </ol>
      </div>
    </section>

    <section title="cache-storage-open"><header><span class="section-number">5.5.3</span> <h4 id="cache-storage-open" data-bookmark-label="5.5.3 open(cacheName)"><code>open(<var>cacheName</var>)</code></h4><span class="anchor"><a style="text-decoration: none;" href="#cache-storage-open">¶</a></span></header>


      <p id="cache-storage-open.1"><dfn id="cache-storage-open-method"><code>open(<var>cacheName</var>)</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>

      <div class="algorithm">
      <ol>
        <li>If the result of running <a href="https://w3c.github.io/webappsec/specs/powerfulfeatures/#settings-secure">is settings object a secure context</a> with the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#incumbent-settings-object">incumbent settings object</a> is <code>Not Secure</code>, return a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with a "<code><a href="http://heycam.github.io/webidl/#securityerror">SecurityError</a></code>" exception.</li>
        <li>Let <var>p</var> be a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a>.</li>
        <li>Run the following substeps:
          <ol>
            <li>For each <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-list-and-record-specification-type">Record</a> {[[key]], [[value]]} <var>entry</var> of its <a href="#dfn-name-to-cache-map">name to cache map</a>, in key insertion order:
              <ol>
                <li>If <var>cacheName</var> matches <var>entry</var>.[[key]], then:
                  <ol>
                    <li>Resolve <var>p</var> with a new <code><a href="#cache-interface">Cache</a></code> object which is a copy of <var>entry</var>.[[value]].</li>
                    <li>Abort these steps.</li>
                  </ol>
                </li>
              </ol>
            </li>
            <li>Let <var>cache</var> be a new <code><a href="#cache-interface">Cache</a></code> object.</li>
            <li>Set a newly-created <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-list-and-record-specification-type">Record</a> {[[key]]: <var>cacheName</var>, [[value]]: <var>cache</var>} to <a href="#dfn-name-to-cache-map">name to cache map</a>. If this cache write operation failed due to exceeding the granted quota limit, reject <var>p</var> with a "<code><a href="http://heycam.github.io/webidl/#quotaexceedederror">QuotaExceededError</a></code>" exception and abort these steps.</li>
            <li>Resolve <var>p</var> with <var>cache</var>.</li>
          </ol>
        </li>
        <li>Return <var>p</var>.</li>
      </ol>
      </div>
    </section>

    <section title="cache-storage-delete"><header><span class="section-number">5.5.4</span> <h4 id="cache-storage-delete" data-bookmark-label="5.5.4 delete(cacheName)"><code>delete(<var>cacheName</var>)</code></h4><span class="anchor"><a style="text-decoration: none;" href="#cache-storage-delete">¶</a></span></header>


      <p id="cache-storage-delete.1"><dfn id="cache-storage-delete-method"><code>delete(<var>cacheName</var>)</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>

      <div class="algorithm">
      <ol>
        <li>If the result of running <a href="https://w3c.github.io/webappsec/specs/powerfulfeatures/#settings-secure">is settings object a secure context</a> with the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#incumbent-settings-object">incumbent settings object</a> is <code>Not Secure</code>, return a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with a "<code><a href="http://heycam.github.io/webidl/#securityerror">SecurityError</a></code>" exception.</li>
        <li>Let <var>p</var> be the result of running the algorithm specified in <code><a href="#cache-storage-has-method">has(<var>cacheName</var>)</a></code> method with <var>cacheName</var> as the argument.</li>
        <li>Return the result of <a href="http://www.w3.org/2001/tag/doc/promises-guide#transforming-by">transforming</a> <var>p</var> with a fulfillment handler that, when called with argument <var>cacheExists</var>, performs the following substeps in parallel:
          <ol>
            <li>If <var>cacheExists</var> is true, then:
              <ol>
                <li>Delete a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-list-and-record-specification-type">Record</a> {[[key]], [[value]]} <var>entry</var> of its <a href="#dfn-name-to-cache-map">name to cache map</a> where <var>cacheName</var> matches entry.[[key]].</li>
                <li>Return true.</li>
                <li>Abort these steps.</li>
              </ol>
            </li>
            <li>Else:
              <ol>
                <li>Return false.</li>
              </ol>
            </li>
          </ol>
        </li>
      </ol>
      </div>
    </section>

    <section title="cache-storage-keys"><header><span class="section-number">5.5.5</span> <h4 id="cache-storage-keys" data-bookmark-label="5.5.5 keys()"><code>keys()</code></h4><span class="anchor"><a style="text-decoration: none;" href="#cache-storage-keys">¶</a></span></header>


      <p id="cache-storage-keys.1"><dfn id="cache-storage-keys-method"><code>keys()</code></dfn> method <em class="rfc2119" title="MUST">must</em> run these steps or their <a href="#dfn-processing-equivalence">equivalent</a>:</p>

      <p class="note" id="cache-storage-keys.2">The promise returned from this method resolves with the sequence of keys, cache names in DOMString, in insertion order.</p>

      <div class="algorithm">
      <ol>
        <li>If the result of running <a href="https://w3c.github.io/webappsec/specs/powerfulfeatures/#settings-secure">is settings object a secure context</a> with the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#incumbent-settings-object">incumbent settings object</a> is <code>Not Secure</code>, return a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with a "<code><a href="http://heycam.github.io/webidl/#securityerror">SecurityError</a></code>" exception.</li>
        <li>Let <var>resultArray</var> be an empty array.</li>
        <li>Return a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> <var>p</var> resolved with the result of running the following substeps:
          <ol>
            <li>For each <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-list-and-record-specification-type">Record</a> {[[key]], [[value]]} <var>entry</var> of its <a href="#dfn-name-to-cache-map">name to cache map</a>, in key insertion order:
              <ol>
                <li>Add <var>entry</var>.[[key]] to <var>resultArray</var>.</li>
              </ol>
            </li>
            <li>Return <var>resultArray</var>.</li>
          </ol>
        </li>
      </ol>
      </div>
    </section>
  </section>
</section>

<section title="security-considerations"><header><span class="section-number">6</span> <h2 id="security-considerations" data-bookmark-label="6 Security Considerations">Security Considerations</h2><span class="anchor"><a style="text-decoration: none;" href="#security-considerations">¶</a></span></header>


  <p id="security-considerations.1"><a href="#dfn-service-worker">Service workers</a> <em class="rfc2119" title="SHOULD">should</em> be implemented to be HTTPS-only. The reasons for SSL-only support include:</p>
  <ul>
    <li>Better to protect end users from man-in-the-middle attacks</li>
    <li>Do good by encouraging HTTPS adoption</li>
    <li>Existing "playground" services (e.g. github.io) now work with HTTPS</li>
    <li>HTTPS is coming across much more of the web quickly</li>
    <li>Devtools can loosen the restriction for development (file://, localhost, etc.)</li>
  </ul>

  <p class="fixme" id="security-considerations.2">The section will be updated.</p>

  <section title="origin-relativity"><header><span class="section-number">6.1</span> <h3 id="origin-relativity" data-bookmark-label="6.1 Origin Relativity">Origin Relativity</h3><span class="anchor"><a style="text-decoration: none;" href="#origin-relativity">¶</a></span></header>


    <p id="origin-relativity.1">One of the advanced concerns that major applications would encounter is whether they can be hosted from a CDN. By definition, these are servers in other places, often on other <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origins</a>. Therefore, <a href="#dfn-service-worker">service workers</a> cannot be hosted on CDNs. But they can include resources via <a href="#importscripts-method">importScripts()</a>. The reason for this restriction is that <a href="#dfn-service-worker">service workers</a> create the opportunity for a bad actor to turn a bad day into a bad eternity.</p>

    <section title="importscripts"><header><span class="section-number">6.1.1</span> <h4 id="importscripts" data-bookmark-label="6.1.1 importScripts(urls)"><code>importScripts(<var>urls</var>)</code></h4><span class="anchor"><a style="text-decoration: none;" href="#importscripts">¶</a></span></header>


      <p class="fixme" id="importscripts.1">The <a href="https://html.spec.whatwg.org/multipage/workers.html#dom-workerglobalscope-importscripts">importScripts(<var>urls</var>)</a> method is defined on the <a href="https://html.spec.whatwg.org/multipage/workers.html#workerglobalscope">WorkerGlobalScope</a> interface. The following algorithm steps monkey patch the method to embrace the <a href="#service-worker-environment">service worker environment</a>. The corresponding change request has been filed in HTML: <a href="https://www.w3.org/Bugs/Public/show_bug.cgi?id=28737">Issue 28737</a>.</p>

      <p id="importscripts.2">When the <dfn id="importscripts-method"><code>importScripts(<var>urls</var>)</code></dfn> method is called on a <code><a href="#service-worker-global-scope-interface">ServiceWorkerGlobalScope</a></code> object, the following steps, or their <a href="#dfn-processing-equivalence">equivalent</a>, <em class="rfc2119" title="MUST">must</em> be run replacing the step 5 of <a href="https://html.spec.whatwg.org/multipage/workers.html#dom-workerglobalscope-importscripts">importScripts(<var>urls</var>)</a>:</p>

      <div class="algorithm">
      <ol>
        <li>Let <var>serviceWorker</var> be the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#incumbent-settings-object">incumbent settings object</a>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#global-object">global object</a>'s <a href="#dfn-service-worker-global-scope-service-worker">service worker</a>.</li>
        <li>If <var>serviceWorker</var>'s <a href="#dfn-imported-scripts-updated-flag">imported scripts updated flag</a> is unset, then:
          <ol>
            <li>Attempt to <a href="https://html.spec.whatwg.org/multipage/infrastructure.html#fetch">fetch</a> each resource identified by the resulting <a href="https://html.spec.whatwg.org/multipage/infrastructure.html#absolute-url">absolute URLs</a>, from the <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a> specified by <em>settings object</em>, using the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#referrer-source">referrer source</a> specified by <em>settings object</em>, and with the <em>blocking flag</em> set.</li>
          </ol>
        </li>
        <li>Else:
          <ol>
            <li>For each <a href="https://html.spec.whatwg.org/multipage/infrastructure.html#absolute-url">absolute URL</a> <var>url</var> in the resulting <a href="https://html.spec.whatwg.org/multipage/infrastructure.html#absolute-url">absolute URLs</a>:
              <ol>
                <li>If there exists a corresponding Record <var>record</var> for <var>url</var> in <var>serviceWorker</var>'s <a href="#dfn-script-resource-map">script resource map</a>, set the script resource used in the step 6 to <var>record</var>.[[value]].</li>
                <li>Else, throw a "<code><a href="http://heycam.github.io/webidl/#networkerror">NetworkError</a></code>" exception.</li>
              </ol>
            </li>
          </ol>
        </li>
      </ol>
      </div>

      <p id="importscripts.3">The following steps, or their <a href="#dfn-processing-equivalence">equivalent</a>, <em class="rfc2119" title="MUST">must</em> be run at the end (as a part) of the step 6.1 of <a href="https://html.spec.whatwg.org/multipage/workers.html#dom-workerglobalscope-importscripts">importScripts(<var>urls</var>)</a>:</p>

      <div class="algorithm">
      <ol>
        <li>If the script resource has been obtained through running <a href="https://html.spec.whatwg.org/multipage/infrastructure.html#fetch">fetch</a>, then:
          <ol>
            <li>If there exists a corresponding Record <var>record</var> for the resulting <a href="https://html.spec.whatwg.org/multipage/infrastructure.html#absolute-url">absolute URL</a> <var>url</var> in <var>serviceWorker</var>'s <a href="#dfn-script-resource-map">script resource map</a>, set <var>record</var>.[[value]] to the fetched script resource.</li>
            <li>Else, set a newly-created Record {[[key]]: <var>url</var>, [[value]]: the fetched script resource} to <var>serviceWorker</var>'s <a href="#dfn-script-resource-map">script resource map</a>.</li>
          </ol>
        </li>
      </ol>
      </div>

      <p id="importscripts.4">The following step, or its <a href="#dfn-processing-equivalence">equivalent</a>, <em class="rfc2119" title="MUST">must</em> be run as the step 7 of <a href="https://html.spec.whatwg.org/multipage/workers.html#dom-workerglobalscope-importscripts">importScripts(<var>urls</var>)</a>:</p>

      <div class="algorithm">
      <ol>
        <li>Set <var>serviceWorker</var>'s <a href="#dfn-imported-scripts-updated-flag">imported scripts updated flag</a> if all the attempts have succeeded without any error.</li>
      </ol>
      </div>
    </section>
  </section>

  <section title="cross-origin-resources"><header><span class="section-number">6.2</span> <h3 id="cross-origin-resources" data-bookmark-label="6.2 Cross-Origin Resources and CORS">Cross-Origin Resources and CORS</h3><span class="anchor"><a style="text-decoration: none;" href="#cross-origin-resources">¶</a></span></header>


    <p id="cross-origin-resources.1">Applications tend to cache items that come from a CDN or other <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a>. It is possible to request many of them directly using &lt;script&gt;, &lt;img&gt;, &lt;video&gt; and &lt;link&gt; elements. It would be hugely limiting if this sort of runtime collaboration broke when offline. Similarly, it is possible to XHR many sorts of off-<a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a> resources when appropriate CORS headers are set.</p>
    <p id="cross-origin-resources.2">ServiceWorkers enable this by allowing <code><a href="#cache-interface">Cache</a></code>s to fetch and cache off-origin items. Some restrictions apply, however. First, unlike same-origin resources which are managed in the <code><a href="#cache-interface">Cache</a></code> as <code><a href="https://fetch.spec.whatwg.org/#response">Response</a></code> objects with the <code>type</code> attribute set to "<code>basic</code>", the objects stored are <code><a href="https://fetch.spec.whatwg.org/#response">Response</a></code> objects with the <code>type</code> attribute set to "<code>opaque</code>". <code><a href="https://fetch.spec.whatwg.org/#response">Response</a></code>s typed "<code>opaque</code>" provide a much less expressive API than <code><a href="https://fetch.spec.whatwg.org/#response">Response</a></code>s typed "<code>basic</code>"; the bodies and headers cannot be read or set, nor many of the other aspects of their content inspected. They can be passed to <code><a href="#fetch-event-respondwith-method">event.respondWith(<var>r</var>)</a></code> method in the same manner as the <code><a href="https://fetch.spec.whatwg.org/#response">Response</a></code>s typed "<code>basic</code>", but cannot be meaningfully created programmatically. These limitations are necessary to preserve the security invariants of the platform. Allowing <code><a href="#cache-interface">Cache</a></code>s to store them allows applications to avoid re-architecting in most cases.</p>
    <p class="fixme" id="cross-origin-resources.3">The section will be updated.</p>
  </section>
</section>

<section title="storage-considerations"><header><span class="section-number">7</span> <h2 id="storage-considerations" data-bookmark-label="7 Storage Considerations">Storage Considerations</h2><span class="anchor"><a style="text-decoration: none;" href="#storage-considerations">¶</a></span></header>


  <p id="storage-considerations.1"><a href="#dfn-service-worker">Service workers</a> <em class="rfc2119" title="SHOULD">should</em> take a dependency on <a href="http://www.w3.org/TR/quota-api/">Quota Management API</a> that <a href="http://www.w3.org/TR/quota-api/#extensions-to-the-serviceworkerglobalscope-interface">extends the ServiceWorkerGlobalScope</a> with the event listeners <a href="http://www.w3.org/TR/quota-api/#widl-ServiceWorkerGlobalScope-onbeforeevicted">onbeforeevicted</a> and <a href="http://www.w3.org/TR/quota-api/#widl-ServiceWorkerGlobalScope-onevicted">onevicted</a> to detect a storage pressure and give pre-eviction information to the application.</p>
  <p id="storage-considerations.2">The cache write operations in <a href="#dfn-service-worker">service workers</a> when failed due to exceeding the granted quota limit <em class="rfc2119" title="SHOULD">should</em> throw "<code><a href="http://www.w3.org/TR/dom/#dom-domexception-quota_exceeded_err">QuotaExceededError</a></code>" exception.</p>
</section>

<section title="extensibility"><header><span class="section-number">8</span> <h2 id="extensibility" data-bookmark-label="8 Extensibility">Extensibility</h2><span class="anchor"><a style="text-decoration: none;" href="#extensibility">¶</a></span></header>


  <p id="extensibility.1"><a href="#dfn-service-worker">Service workers</a> are extensible from other specifications.</p>

  <section title="extension-to-service-worker-registration"><header><span class="section-number">8.1</span> <h3 id="extension-to-service-worker-registration" data-bookmark-label="8.1 Define API bound to Service Worker Registration">Define API bound to Service Worker Registration</h3><span class="anchor"><a style="text-decoration: none;" href="#extension-to-service-worker-registration">¶</a></span></header>

    <p id="extension-to-service-worker-registration.1">Specifications <em class="rfc2119" title="MAY">may</em> define an API tied to a <a href="#dfn-service-worker-registration">service worker registration</a> by using <a href="http://heycam.github.io/webidl/#dfn-partial-interface">partial interface</a> definition to the <code><a href="#service-worker-registration-interface">ServiceWorkerRegistration</a></code> interface where it <em class="rfc2119" title="MAY">may</em> define the specification specific attributes and methods:</p>

    <pre><code>partial interface ServiceWorkerRegistration {
  // e.g. define an API namespace
  readonly attribute APISpaceType APISpace;
  // e.g. define a method
  Promise&lt;T&gt; methodName(<em>list of arguments</em>);
};
</code></pre>
  </section>

  <section title="extension-to-extendable-event"><header><span class="section-number">8.2</span> <h3 id="extension-to-extendable-event" data-bookmark-label="8.2 Define Functional Event">Define Functional Event</h3><span class="anchor"><a style="text-decoration: none;" href="#extension-to-extendable-event">¶</a></span></header>

    <p id="extension-to-extendable-event.1">Specifications <em class="rfc2119" title="MAY">may</em> define a <a href="#dfn-functional-events">functional event</a> by extending <code><a href="#extendable-event-interface">ExtendableEvent</a></code> interface:</p>

    <pre><code>// e.g. define FunctionalEvent interface
interface FunctionalEvent : ExtendableEvent {
  // add a functional event's own attributes and methods
};
</code></pre>
  </section>

  <section title="extension-to-service-worker-global-scope"><header><span class="section-number">8.3</span> <h3 id="extension-to-service-worker-global-scope" data-bookmark-label="8.3 Define Event Handler">Define Event Handler</h3><span class="anchor"><a style="text-decoration: none;" href="#extension-to-service-worker-global-scope">¶</a></span></header>

    <p id="extension-to-service-worker-global-scope.1">Specifications <em class="rfc2119" title="MAY">may</em> define an event handler attribute for the corresponding <a href="#dfn-functional-events">functional event</a> using <a href="http://heycam.github.io/webidl/#dfn-partial-interface">partial interface</a> definition to the <code><a href="#service-worker-global-scope-interface">ServiceWorkerGlobalScope</a></code> interface:</p>

    <pre><code>partial interface ServiceWorkerGlobalScope {
  attribute EventHandler on<em>functionalevent</em>;
};</code></pre>
  </section>

  <section title="request-functional-event-dispatch"><header><span class="section-number">8.4</span> <h3 id="request-functional-event-dispatch" data-bookmark-label="8.4 Request Functional Event Dispatch">Request Functional Event Dispatch</h3><span class="anchor"><a style="text-decoration: none;" href="#request-functional-event-dispatch">¶</a></span></header>

    <p id="request-functional-event-dispatch.1">To request a <a href="#dfn-functional-events">functional event</a> dispatch to a <a href="#dfn-service-worker">service worker</a>, specifications <em class="rfc2119" title="MAY">may</em> invoke <a href="#handle-functional-event-algorithm">Handle Functional Event</a> algorithm, or its <a href="#dfn-processing-equivalence">equivalent</a>, with its <a href="#dfn-service-worker-registration">service worker registration</a> <var>registration</var> and the algorithm <var>callbackSteps</var> as the arguments.</p>

    <p id="request-functional-event-dispatch.2">Specifications <em class="rfc2119" title="MAY">may</em> define an algorithm <var>callbackSteps</var> where the corresponding <a href="#dfn-functional-events">functional event</a> can be created and fired with specification specific objects. The algorithm is passed <var>globalObject</var> (a <a href="#service-worker-global-scope-interface">ServiceWorkerGlobalScope</a> object) at which it <em class="rfc2119" title="MAY">may</em> fire its <a href="#dfn-functional-events">functional events</a>. This algorithm is called on a <a href="https://html.spec.whatwg.org/multipage/webappapis.html#concept-task">task</a> <a href="https://html.spec.whatwg.org/multipage/webappapis.html#queue-a-task">queued</a> by <a href="#handle-functional-event-algorithm">Handle Functional Event</a> algorithm.</p>

    <p class="note" id="request-functional-event-dispatch.3">See an <a href="https://notifications.spec.whatwg.org/#activating-a-notification">example</a> hook defined in <a href="https://notifications.spec.whatwg.org">Notifications API</a>.</p>
  </section>
</section>

<section title="algorithms"><header><span class="section-number">9</span> <h2 id="algorithms" data-bookmark-label="9 Appendix A: Algorithms">Appendix A: Algorithms</h2><span class="anchor"><a style="text-decoration: none;" href="#algorithms">¶</a></span></header>


  <p id="algorithms.1">The following definitions are the user agent's internal data structures used throughout the specification.</p>

  <p id="algorithms.2">A <dfn id="dfn-scope-to-registration-map">scope to registration map</dfn> is a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-list-and-record-specification-type">List</a> of the <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-list-and-record-specification-type">Record</a> {[[key]], [[value]]} where [[key]] is a string that represents a <a href="#dfn-scope-url">scope url</a> and [[value]] is a <a href="#dfn-service-worker-registration">service worker registration</a>.</p>

  <p id="algorithms.3">An <dfn id="dfn-algorithm-task-queue">algorithm thread queue</dfn> is a thread safe queue used to synchronize the set of concurrent entries of algorithm steps. The queue contains <a href="https://en.wikipedia.org/wiki/Timestamping_(computing)">timestamps</a> (with <a href="https://en.wikipedia.org/wiki/Timestamp-based_concurrency_control#Assumptions">the assumptions</a>), gained by algorithms, as its elements. The queue <em class="rfc2119" title="SHOULD">should</em> satisfy the general properties of FIFO queue.</p>

  <p id="algorithms.4">A <dfn id="dfn-registration-queue-adt">registration queue</dfn> is  an <a href="#dfn-algorithm-task-queue">algorithm thread queue</a> for synchronizing the set of concurrent registration requests. The user agent <em class="rfc2119" title="MUST">must</em> maintain a separate queue for each <a href="#dfn-service-worker-registration">service worker registration</a> keyed by its <a href="#dfn-scope-url">scope url</a>. The queue is initially empty.</p>

  <p id="algorithms.5">An <dfn id="dfn-installation-queue-adt">installation queue</dfn> is an <a href="#dfn-algorithm-task-queue">algorithm thread queue</a> for synchronizing the set of concurrent installation jobs. The user agent <em class="rfc2119" title="MUST">must</em> maintain a separate queue for each <a href="#dfn-service-worker-registration">service worker registration</a> keyed by its <a href="#dfn-scope-url">scope url</a>. The queue is initially empty.</p>

  <p id="algorithms.6">An <dfn id="dfn-installation-result-handle-queue-adt">installation result handle queue</dfn> is an <a href="#dfn-algorithm-task-queue">algorithm thread queue</a> for synchronizing the set of concurrent installation jobs. The user agent <em class="rfc2119" title="MUST">must</em> maintain a separate queue for each <a href="#dfn-service-worker-registration">service worker registration</a> keyed by its <a href="#dfn-scope-url">scope url</a>. The queue is initially empty.</p>

  <p id="algorithms.7">An <dfn id="dfn-activation-queue-adt">activation queue</dfn> is an <a href="#dfn-algorithm-task-queue">algorithm thread queue</a> for synchronizing the set of concurrent installation jobs. The user agent <em class="rfc2119" title="MUST">must</em> maintain a separate queue for each <a href="#dfn-service-worker-registration">service worker registration</a> keyed by its <a href="#dfn-scope-url">scope url</a>. The queue is initially empty.</p>

  <section title="register-algorithm"><header><span class="section-number">9.1</span> <h3 id="register-algorithm" data-bookmark-label="9.1 Register">Register</h3><span class="anchor"><a style="text-decoration: none;" href="#register-algorithm">¶</a></span></header>


    <div class="algorithm">
    <dl>
      <dt>Input</dt>
        <dd><var>client</var>, a <a href="#dfn-service-worker-client">service worker client</a></dd>
        <dd><var>scriptURL</var>, an <a href="https://url.spec.whatwg.org/#concept-absolute-url">absolute URL</a></dd>
        <dd><var>scopeURL</var>, an <a href="https://url.spec.whatwg.org/#concept-absolute-url">absolute URL</a></dd>
      <dt>Output</dt>
        <dd><var>promise</var>, a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a></dd>
    </dl>
    <ol>
      <li>If the result of running <a href="https://w3c.github.io/webappsec/specs/powerfulfeatures/#is-origin-trustworthy">Is origin potentially trustworthy</a> with the <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a> of <var>scriptURL</var> as the argument is <code>Not Trusted</code>, then:
        <ol>
          <li>Return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with a "<code><a href="http://heycam.github.io/webidl/#securityerror">SecurityError</a></code>" exception.</li>
        </ol>
      </li>
      <li>If the <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a> of <var>scriptURL</var> is not <var>client</var>'s <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a>, then:
        <ol>
          <li>Return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with a "<code><a href="http://heycam.github.io/webidl/#securityerror">SecurityError</a></code>" exception.</li>
        </ol>
      </li>
      <li>If the <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a> of <var>scopeURL</var> is not <var>client</var>'s <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a>, then:
        <ol>
          <li>Return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> rejected with a "<code><a href="http://heycam.github.io/webidl/#securityerror">SecurityError</a></code>" exception.</li>
        </ol>
      </li>
      <li>Run the following substeps atomically:
        <ol>
          <li>Let <var>registration</var> be the result of running the <a href="#get-registration-algorithm">Get Registration</a> algorithm passing <var>scopeURL</var> as the argument.</li>

          <li>If <var>registration</var> is not null, then:
            <ol>
              <li>Let <var>newestWorker</var> be the result of running the <a href="#get-newest-worker-algorithm">Get Newest Worker</a> algorithm passing <var>registration</var> as the argument.</li>
              <li>If <var>newestWorker</var> is not null, <var>scriptURL</var> is equal to <var>newestWorker</var>'s <a href="#dfn-script-url">script url</a>, and <var>scriptURL</var> is equal to <var>registration</var>'s <a href="#dfn-registration-script-url">registering script url</a>, then:
                <ol>
                  <li>If <var>newestWorker</var> is an <a href="#dfn-active-worker">active worker</a>, then:
                    <ol>
                      <li>If <var>registration</var>'s <a href="#dfn-uninstalling-flag">uninstalling flag</a> is set, unset it.</li>
                      <li>Return a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> resolved with a <code><a href="#service-worker-registration-interface">ServiceWorkerRegistration</a></code> object, setting its <a href="#dfn-service-worker-registration-interface-client">service worker client</a> to <var>client</var>, which represents <var>registration</var>.</li>
                    </ol>
                  </li>
                </ol>
              </li>
            </ol>
          </li>
          <li>Else:
            <ol>
              <li>Set <var>registration</var> to the result of running <a href="#set-registration-algorithm">Set Registration</a> algorithm passing <var>scopeURL</var> as its argument.</li>
            </ol>
          </li>
          <li>Set <var>registration</var>'s <a href="#dfn-registration-script-url">registering script url</a> to <var>scriptURL</var>.</li>
          <li>Return the result of running the <a href="#update-algorithm">Update</a> algorithm, or its <a href="#dfn-processing-equivalence">equivalent</a>, passing <var>client</var> and <var>registration</var> as the argument.</li>
        </ol>
      </li>
    </ol>
    </div>
  </section>

  <section title="update-algorithm"><header><span class="section-number">9.2</span> <h3 id="update-algorithm" data-bookmark-label="9.2 Update">Update</h3><span class="anchor"><a style="text-decoration: none;" href="#update-algorithm">¶</a></span></header>


    <p id="update-algorithm.1">The algorithm uses <a href="#dfn-registration-queue-adt">registration queue</a> to synchronize the set of multiple registration requests. Implementers <em class="rfc2119" title="MAY">may</em> use it or other synchronization primitives and methods to satisfy this requirement.</p>

  <!--
  #FIXME: (Checkpoint) This is a platform implmentation not exposing APIs to userland. As such, promise is not used for its output.
  -->
    <div class="algorithm">
    <dl>
      <dt>Input</dt>
        <dd><var>client</var>, a <a href="#dfn-service-worker-client">service worker client</a></dd>
        <dd><var>registration</var>, a <a href="#dfn-service-worker-registration">service worker registration</a></dd>
      <dt>Output</dt>
        <dd><var>promise</var>, a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a></dd>
    </dl>
    <ol>
      <li>Let <var>p</var> be a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a>.</li>
      <li><a href="https://en.wikipedia.org/wiki/Timestamp-based_concurrency_control#Generating_a_Timestamp">Generate a timestamp</a> and let <var>timeStamp</var> be the result value.</li>
      <li>Push <var>timeStamp</var> to <a href="#dfn-registration-queue-adt">registration queue</a>, <a href="#dfn-installation-queue-adt">installation queue</a>, and <a href="#dfn-installation-result-handle-queue-adt">installation result handle queue</a>.</li>
      <li>Run the following substeps in parallel:
        <ol>
          <li><em>CheckPriority</em>: If the value of the top element of <a href="#dfn-registration-queue-adt">registration queue</a> is not <var>timeStamp</var>, then:
            <ol>
              <li>Wait until the top element of <a href="#dfn-registration-queue-adt">registration queue</a> is popped.</li>
              <li>Jump to the step labeled <em>CheckPriority</em>.</li>
            </ol>
            <p class="note"><em>Wait</em> is a blocking wait. Implementers may use a condition variable or its equivalent synchronization primitive.</p>
          </li>
          <li>If <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a> is not null, then:
            <ol>
              <li><a href="https://html.spec.whatwg.org/multipage/workers.html#terminate-a-worker">Terminate</a> <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a>.</li>
              <li>Run the <a href="#update-state-algorithm">Update State</a> algorithm passing <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a> and <em>redundant</em> as the arguments.</li>
              <li>Set <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a> to null.</li>
              <li>The user agent <em class="rfc2119" title="MAY">may</em> abort in-flight requests triggered by <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a>.</li>
            </ol>
          </li>
          <li>Let <var>r</var> be the associated <a href="https://fetch.spec.whatwg.org/#concept-request">request</a> of the result of invoking the initial value of <a href="https://fetch.spec.whatwg.org/#dom-request">Request</a> as constructor with <var>registration</var>'s <a href="https://url.spec.whatwg.org/#concept-url-serializer">serialized</a> <a href="#dfn-registration-script-url">registering script url</a>. If this <a href="http://heycam.github.io/webidl/#dfn-throw">throws</a> an exception, then:
            <ol>
              <li>Reject <var>p</var> with the exception.</li>
              <li>Pop the top element from <a href="#dfn-registration-queue-adt">registration queue</a>, <a href="#dfn-installation-queue-adt">installation queue</a> and <a href="#dfn-installation-result-handle-queue-adt">installation result handle queue</a>.</li>
              <li>If the result of running <a href="#get-newest-worker-algorithm">Get Newest Worker</a> algorithm passing <var>registration</var> as the argument is null, invoke <a href="#clear-registration-algorithm">Clear Registration</a> algorithm passing <var>registration</var> as its argument.</li>
              <li>Abort these steps.</li>
            </ol>
          </li>
          <li>Set <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-context">context</a> to <em>serviceworker</em>.</li>
          <li>Set <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-client">client</a> to <var>client</var>.</li>
          <li>Append `<code>Service-Worker</code>`/`<code>script</code>` to <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-header-list">header list</a>.</li>
          <li>Set <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#skip-service-worker-flag">skip service worker flag</a>, <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#synchronous-flag">synchronous flag</a>, and <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-redirect-mode">redirect mode</a> to "<code>manual</code>".</li>
          <li>Let <var>response</var> be the result of running <a href="https://fetch.spec.whatwg.org/#concept-fetch">fetch</a> using <var>r</var>, forcing a network fetch if cached entry is greater than 1 day old.</li>
          <li>If <var>response</var> is a <a href="https://fetch.spec.whatwg.org/#concept-network-error">network error</a> or <var>response</var>'s <a href="https://fetch.spec.whatwg.org/#concept-response-status">status</a> is not in the range 200 to 299, then:
            <ol>
              <li>Reject <var>p</var> with a <code>TypeError</code>.</li>
              <li>Pop the top element from <a href="#dfn-registration-queue-adt">registration queue</a>, <a href="#dfn-installation-queue-adt">installation queue</a> and <a href="#dfn-installation-result-handle-queue-adt">installation result handle queue</a>.</li>
              <li>If the result of running <a href="#get-newest-worker-algorithm">Get Newest Worker</a> algorithm passing <var>registration</var> as the argument is null, invoke <a href="#clear-registration-algorithm">Clear Registration</a> algorithm passing <var>registration</var> as its argument.</li>
              <li>Abort these steps.</li>
            </ol>
          </li>
          <li><a href="https://fetch.spec.whatwg.org/#concept-header-extract-mime-type">Extract a MIME type</a> from the <var>response</var>'s <a href="https://fetch.spec.whatwg.org/#concept-response-header-list">header list</a>. If this MIME type (ignoring parameters) is not one of <code>text/javascript</code>, <code>application/x-javascript</code>, and <code>application/javascript</code>, then:
            <ol>
              <li>Reject <var>p</var> with a "<code><a href="http://heycam.github.io/webidl/#securityerror">SecurityError</a></code>" exception.</li>
              <li>Pop the top element from <a href="#dfn-registration-queue-adt">registration queue</a>, <a href="#dfn-installation-queue-adt">installation queue</a> and <a href="#dfn-installation-result-handle-queue-adt">installation result handle queue</a>.</li>
              <li>If the result of running <a href="#get-newest-worker-algorithm">Get Newest Worker</a> algorithm passing <var>registration</var> as the argument is null, invoke <a href="#clear-registration-algorithm">Clear Registration</a> algorithm passing <var>registration</var> as its argument.</li>
              <li>Abort these steps.</li>
            </ol>
          </li>
          <li>Let <var>serviceWorkerAllowed</var> be the result of <a href="https://fetch.spec.whatwg.org/#concept-header-parse">parsing</a> `<code>Service-Worker-Allowed</code>` in <var>response</var>'s <a href="https://fetch.spec.whatwg.org/#concept-response-header-list">header list</a>.</li>
          <li>If <var>serviceWorkerAllowed</var> is failure, then:
            <ol>
              <li>Reject <var>p</var> with a <code>TypeError</code>.</li>
              <li>Pop the top element from <a href="#dfn-registration-queue-adt">registration queue</a>, <a href="#dfn-installation-queue-adt">installation queue</a> and <a href="#dfn-installation-result-handle-queue-adt">installation result handle queue</a>.</li>
              <li>If the result of running <a href="#get-newest-worker-algorithm">Get Newest Worker</a> algorithm passing <var>registration</var> as the argument is null, invoke <a href="#clear-registration-algorithm">Clear Registration</a> algorithm passing <var>registration</var> as its argument.</li>
              <li>Abort these steps.</li>
            </ol>
          </li>
          <li>Let <var>scopeURL</var> be <var>registration</var>'s <a href="#dfn-scope-url">scope url</a>.</li>
          <li>Let <var>maxScopeString</var> be null.</li>
          <li>If <var>serviceWorkerAllowed</var> is null, then:
            <ol>
              <li>Set <var>maxScopeString</var> to "<code>/</code>" concatenated with the strings, except the last string that denotes the script's file name, in <var>registration</var>'s <a href="#dfn-registration-script-url">registering script url</a>'s <a href="https://url.spec.whatwg.org/#concept-url-path">path</a> (including empty strings), separated from each other by "<code>/</code>".</li>
            </ol>
          </li>
          <li>Else:
            <ol>
              <li>Let <var>maxScope</var> be the result of <a href="https://url.spec.whatwg.org/#concept-url-parser">parsing</a> <var>serviceWorkerAllowed</var> with <var>registration</var>'s <a href="#dfn-registration-script-url">registering script url</a>.</li>
              <li>Set <var>maxScopeString</var> to "<code>/</code>" concatenated with the strings in <var>maxScope</var>'s <a href="https://url.spec.whatwg.org/#concept-url-path">path</a> (including empty strings), separated from each other by "<code>/</code>".</li>
            </ol>
          </li>
          <li>Let <var>scopeString</var> be "<code>/</code>" concatenated with the strings in <var>scopeURL</var>'s <a href="https://url.spec.whatwg.org/#concept-url-path">path</a> (including empty strings), separated from each other by "<code>/</code>".</li>
          <li>If <var>scopeString</var> starts with <var>maxScopeString</var>, do nothing.</li>
          <li>Else:
            <ol>
              <li>Reject <var>p</var> with a "<code><a href="http://heycam.github.io/webidl/#securityerror">SecurityError</a></code>" exception.</li>
              <li>Pop the top element from <a href="#dfn-registration-queue-adt">registration queue</a>, <a href="#dfn-installation-queue-adt">installation queue</a> and <a href="#dfn-installation-result-handle-queue-adt">installation result handle queue</a>.</li>
              <li>If the result of running <a href="#get-newest-worker-algorithm">Get Newest Worker</a> algorithm passing <var>registration</var> as the argument is null, invoke <a href="#clear-registration-algorithm">Clear Registration</a> algorithm passing <var>registration</var> as its argument.</li>
              <li>Abort these steps.</li>
            </ol>
          </li>
          <li>Let <var>newestWorker</var> be the result of running the <a href="#get-newest-worker-algorithm">Get Newest Worker</a> algorithm passing <var>registration</var> as the argument.</li>
          <li>If <var>newestWorker</var> is not null, and <var>newestWorker</var>'s <a href="#dfn-script-url">script url</a> is equal to <var>registration</var>'s <a href="#dfn-registration-script-url">registering script url</a> and <var>response</var> is a byte-for-byte match with the script resource of <var>newestWorker</var>, then:
            <ol>
              <li>Resolve <var>p</var> with a <code><a href="#service-worker-registration-interface">ServiceWorkerRegistration</a></code> object, setting its <a href="#dfn-service-worker-registration-interface-client">service worker client</a> to <var>client</var>, which represents <var>registration</var>.</li>
              <li>Abort these steps.</li>
            </ol>
          </li>
          <li>Else:
            <ol>
              <li>Let <var>worker</var> be a new <a href="#dfn-service-worker">service worker</a>.</li>
              <li>Set <var>worker</var>'s <a href="#dfn-script-url">script url</a> to <var>registration</var>'s <a href="#dfn-registration-script-url">registering script url</a>. (<var>worker</var>'s script resource is the fetched <var>response</var>.) Generate a new <a href="http://tools.ietf.org/html/rfc4122#section-3">UUID</a> and set <var>worker</var>'s <a href="#dfn-service-worker-id">id</a> to the value.</li>
              <li>Invoke <a href="#run-service-worker-algorithm">Run Service Worker</a> algorithm with <var>worker</var> as the arguement.</li>
              <li>If an uncaught runtime script error occurs during the above step, then:
                <ol>
                  <li>Reject <var>p</var> with the error.</li>
                  <li>Pop the top element from <a href="#dfn-registration-queue-adt">registration queue</a>, <a href="#dfn-installation-queue-adt">installation queue</a> and <a href="#dfn-installation-result-handle-queue-adt">installation result handle queue</a>.</li>
                  <li>If the result of running <a href="#get-newest-worker-algorithm">Get Newest Worker</a> algorithm passing <var>registration</var> as its argument is null, then:
                    <ol>
                      <li>Invoke <a href="#clear-registration-algorithm">Clear Registration</a> algorithm passing <var>registration</var> as its argument.</li>
                    </ol>
                  </li>
                  <li>Abort these steps.</li>
                </ol>
              </li>
            </ol>
          </li>
          <li>Pop the top element from <a href="#dfn-registration-queue-adt">registration queue</a>.</li>
          <li>Invoke <a href="#installation-algorithm">Install</a> algorithm, or its <a href="#dfn-processing-equivalence">equivalent</a>, with <var>client</var>, <var>registration</var>, <var>worker</var>, <var>p</var>, and <var>timeStamp</var> as its arguments.</li>
        </ol>
      </li>
      <li>Return <var>p</var>.</li>
    </ol>
    </div>
  </section>

  <section title="soft-update-algorithm"><header><span class="section-number">9.3</span> <h3 id="soft-update-algorithm" data-bookmark-label="9.3 Soft Update">Soft Update</h3><span class="anchor"><a style="text-decoration: none;" href="#soft-update-algorithm">¶</a></span></header>


    <p id="soft-update-algorithm.1">The user agent <em class="rfc2119" title="MAY">may</em> call this as often as it likes to check for updates.</p>

    <div class="algorithm">
    <dl>
      <dt>Input</dt>
        <dd><var>registration</var>, a <a href="#dfn-service-worker-registration">service worker registration</a></dd>
      <dt>Output</dt>
        <dd>None</dd>
    </dl>
    <ol>
      <li>Let <var>client</var> be null.</li>
      <li>If <var>registration</var>'s <a href="#dfn-uninstalling-flag">uninstalling flag</a> is set, abort these steps.</li>
      <li>If <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a> is not null, abort these steps.</li>
      <li>Let <var>newestWorker</var> be the result of running <a href="#get-newest-worker-algorithm">Get Newest Worker</a> algorithm passing <var>registration</var> as its argument.</li>
      <li>If <var>newestWorker</var> is null, abort these steps.</li>
      <li>Set <var>registration</var>'s <a href="#dfn-registration-script-url">registering script url</a> to <var>newestWorker</var>'s <a href="#dfn-script-url">script url</a>.</li>
      <li>Invoke <a href="#update-algorithm">Update</a> algorithm, or its <a href="#dfn-processing-equivalence">equivalent</a>, with <var>client</var>, <var>registration</var> as its argument.</li>
    </ol>
    </div>
  </section>

  <section title="installation-algorithm"><header><span class="section-number">9.4</span> <h3 id="installation-algorithm" data-bookmark-label="9.4 Install">Install</h3><span class="anchor"><a style="text-decoration: none;" href="#installation-algorithm">¶</a></span></header>


    <p id="installation-algorithm.1">The algorithm uses <a href="#dfn-installation-queue-adt">installation queue</a> to synchronize the set of multiple installation jobs. Implementers <em class="rfc2119" title="MAY">may</em> use it or other synchronization primitives and methods to satisfy this requirement.</p>

    <div class="algorithm">
    <dl>
      <dt>Input</dt>
        <dd><var>client</var>, a <a href="#dfn-service-worker-client">service worker client</a></dd>
        <dd><var>registration</var>, a <a href="#dfn-service-worker-registration">service worker registration</a></dd>
        <dd><var>worker</var>, a <a href="#dfn-service-worker">service worker</a></dd>
        <dd><var>registrationPromise</var>, a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a></dd>
        <dd><var>timeStamp</var>, a <a href="https://en.wikipedia.org/wiki/Timestamping_(computing)">timestamp</a></dd>
      <dt>Output</dt>
        <dd>none</dd>
    </dl>
    <ol>
      <li>Let <var>installFailed</var> be false.</li>
      <li><em>CheckPriority</em>: If the value of the top element of <a href="#dfn-installation-queue-adt">installation queue</a> is not <var>timeStamp</var>, then:
        <ol>
          <li>Wait until the top element of <a href="#dfn-installation-queue-adt">installation queue</a> is popped.</li>
          <li>Jump to the step labeled <em>CheckPriority</em>.</li>
        </ol>
        <p class="note"><em>Wait</em> is a blocking wait. Implementers may use a condition variable or its equivalent synchronization primitive.</p>
      </li>
      <li>If <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a> is not null, then:
        <ol>
          <li><a href="https://html.spec.whatwg.org/multipage/workers.html#terminate-a-worker">Terminate</a> <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a>.</li>
          <li>Run the <a href="#update-state-algorithm">Update State</a> algorithm passing <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a> and <em>redundant</em> as the arguments.</li>
          <li>The user agent <em class="rfc2119" title="MAY">may</em> abort any in-flight requests triggered by <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a>.</li>
        </ol>
      </li>
      <li>Set <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a> to <var>worker</var>.</li>
      <li>Run the <a href="#update-state-algorithm">Update State</a> algorithm passing <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a> and <em>installing</em> as the arguments.</li>
      <li><a href="http://www.ecma-international.org/ecma-262/6.0/#sec-algorithm-conventions">Assert</a>: <var>registrationPromise</var> is not null.</li>
      <li>Resolve <var>registrationPromise</var> with a <code><a href="#service-worker-registration-interface">ServiceWorkerRegistration</a></code> object, setting its <a href="#dfn-service-worker-registration-interface-client">service worker client</a> to <var>client</var>, which represents <var>registration</var>.</li>
      <li><a href="https://html.spec.whatwg.org/multipage/webappapis.html#queue-a-task">Queue a task</a> to <a href="https://html.spec.whatwg.org/#fire-a-simple-event">fire a simple event named</a> <code>updatefound</code> at all the <code><a href="#service-worker-registration-interface">ServiceWorkerRegistration</a></code> objects that represent <var>registration</var> for all the <a href="#dfn-service-worker-client">service worker clients</a> whose <a href="https://www.w3.org/Bugs/Public/show_bug.cgi?id=27146">creation url</a> <a href="#scope-match-algorithm">matches</a> <var>registration</var>'s <a href="#dfn-scope-url">scope url</a>.</li>
      <li>Let <var>installingWorker</var> be <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a>.</li>
      <li>Invoke <a href="#run-service-worker-algorithm">Run Service Worker</a> algorithm with <var>installingWorker</var> as the arguement.</li>
      <li><a href="https://html.spec.whatwg.org/multipage/webappapis.html#queue-a-task">Queue a task</a> <var>task</var> to run the following substeps:
        <ol>
          <li>Create a <a href="https://html.spec.whatwg.org/#concept-events-trusted">trusted</a> event <var>e</var> that uses the <code><a href="#extendable-event-interface">ExtendableEvent</a></code> interface, with the event type <code><a href="#service-worker-global-scope-install-event">install</a></code>, which does not bubble, is not cancelable, and has no default action.</li>
          <li><a href="https://html.spec.whatwg.org/multipage/infrastructure.html#concept-event-dispatch">Dispatch</a> <var>e</var> at <var>installingWorker</var>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#environment-settings-object"> environment settings object</a>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#global-object">global object</a>.</li>
          <li>Let <var>extendLifetimePromises</var> be an empty array.</li>
          <li>For each <a href="https://dom.spec.whatwg.org/#concept-event-listener">event listener</a> <a href="https://dom.spec.whatwg.org/#concept-event-listener-invoke">invoked</a>:
            <ol>
              <li>If any uncaught runtime script error occurs, then:
                <ol>
                  <li><a href="https://html.spec.whatwg.org/multipage/webappapis.html#report-the-error">Report the error</a> for the script per the <a href="https://html.spec.whatwg.org/multipage/workers.html#runtime-script-errors-2">runtime script errors handling</a>.</li>
                  <li>Run the <a href="#update-state-algorithm">Update State</a> algorithm passing <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a> and <em>redundant</em> as the arguments.</li>
                  <li>Set <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a> to null.</li>
                  <li>Pop the top element from <a href="#dfn-installation-queue-adt">installation queue</a> and <a href="#dfn-installation-result-handle-queue-adt">installation result handle queue</a>.</li>
                  <li>If the result of running <a href="#get-newest-worker-algorithm">Get Newest Worker</a> algorithm is null, then:
                    <ol>
                      <li>Invoke <a href="#clear-registration-algorithm">Clear Registration</a> algorithm passing <var>registration</var> as its argument.</li>
                    </ol>
                  </li>
                  <li>Abort these steps.</li>
                </ol>
              </li>
              <li>Let <var>eventObject</var> be the first argument passed to this <a href="https://dom.spec.whatwg.org/#concept-event-listener">event listener</a>.</li>
              <li>Append <var>eventObject</var>'s <a href="#dfn-extend-lifetime-promises">extend lifetime promises</a> to <var>extendLifetimePromises</var>.</li>
            </ol>
          </li>
          <li>Let <var>p</var> be <a href="http://www.w3.org/2001/tag/doc/promises-guide#waiting-for-all">waiting for all of</a> <var>extendLifetimePromises</var>.</li>
          <li>Run the following substeps in parallel:
            <ol>
              <li>Wait until <var>p</var> settles.</li>
              <li>If <var>p</var> rejected, then:
                <ol>
                  <li>Set <var>installFailed</var> to true.</li>
                </ol>
              </li>
              <li>Else if <var>p</var> resolved with a value, then:
                <ol>
                  <li>Do nothing.</li>
                </ol>
              </li>
            </ol>
          </li>
        </ol>
      </li>
      <li>Pop the top element from <a href="#dfn-installation-queue-adt">installation queue</a>.</li>
      <li><em>CheckResultHandlePriority</em>: If the value of the top element of <a href="#dfn-installation-result-handle-queue-adt">installation result handle queue</a> is not <var>timeStamp</var>, then:
        <ol>
          <li>Wait until the top element of <a href="#dfn-installation-result-handle-queue-adt">installation result handle queue</a> is popped.</li>
          <li>Jump to the step labeled <em>CheckResultHandlePriority</em>.</li>
        </ol>
        <p class="note"><em>Wait</em> is a blocking wait. Implementers may use a condition variable or its equivalent synchronization primitive.</p>
        <p>If <var>task</var> is discarded or the script has been aborted by the <a href="https://html.spec.whatwg.org/multipage/workers.html#terminate-a-worker">termination</a> of <var>installingWorker</var>, set <var>installFailed</var> to true.</p>
      </li>
      <li>Wait for <var>task</var> to have executed or been discarded.</li>
      <li>If <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a> is null, then:
        <ol>
          <li>Abort these steps.</li>
        </ol>
      </li>
      <li>If <var>installFailed</var> is true, then:
        <ol>
          <li>Run the <a href="#update-state-algorithm">Update State</a> algorithm passing <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a> and <em>redundant</em> as the arguments.</li>
          <li>Set <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a> to null.</li>
          <li>If the result of running <a href="#get-newest-worker-algorithm">Get Newest Worker</a> algorithm is null, then:
            <ol>
              <li>Invoke <a href="#clear-registration-algorithm">Clear Registration</a> algorithm passing <var>registration</var> as its argument.</li>
            </ol>
          </li>
          <li>Abort these steps.</li>
        </ol>
      </li>
      <li>If <var>registration</var>'s <a href="#dfn-waiting-worker">waiting worker</a> is not null, then:
        <ol>
          <li><a href="https://html.spec.whatwg.org/multipage/workers.html#terminate-a-worker">Terminate</a> <var>registration</var>'s <a href="#dfn-waiting-worker">waiting worker</a>.</li>
          <li>Run the <a href="#update-state-algorithm">Update State</a> algorithm passing <var>registration</var>'s <a href="#dfn-waiting-worker">waiting worker</a> and <em>redundant</em> as the arguments.</li>
          <li>The user agent <em class="rfc2119" title="MAY">may</em> abort in-flight requests triggered by <var>registration</var>'s <a href="#dfn-waiting-worker">waiting worker</a>.</li>
        </ol>
      </li>
      <li>Set <var>registration</var>'s <a href="#dfn-waiting-worker">waiting worker</a> to <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a>.</li>
      <li>Set <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a> to null.</li>
      <li>Run the <a href="#update-state-algorithm">Update State</a> algorithm passing <var>registration</var>'s <a href="#dfn-waiting-worker">waiting worker</a> and <em>installed</em> as the arguments.</li>
      <li>If <var>registration</var>'s <a href="#dfn-uninstalling-flag">uninstalling flag</a> is set, then:
        <ol>
          <li>If it was set before <var>timeStamp</var>, unset <var>registration</var>'s <a href="#dfn-uninstalling-flag">uninstalling flag</a>.</li>
          <li>Else, abort these steps.</li>
        </ol>
      </li>
      <li>If <var>registration</var>'s <a href="#dfn-waiting-worker">waiting worker</a>'s <a href="#dfn-skip-waiting-flag">skip waiting flag</a> is set, then:
        <ol>
          <li>For each <a href="#dfn-service-worker-client">service worker client</a> <var>serviceWorkerClient</var> whose <a href="https://www.w3.org/Bugs/Public/show_bug.cgi?id=27146">creation url</a> <a href="#scope-match-algorithm">matches</a> <var>registration</var>'s <a href="#dfn-scope-url">scope url</a>:
            <ol>
              <li>Let <var>exitingWorker</var> be the <a href="#dfn-active-worker">active worker</a> that <a href="#dfn-control">controls</a> <var>serviceWorkerClient</var>.</li>
              <li>If <var>exitingWorker</var> is not null, then:
                <ol>
                  <li>Wait for <var>exitingWorker</var> to finish handling any in-progress requests.
                  </li>
                  <li><a href="https://html.spec.whatwg.org/multipage/workers.html#terminate-a-worker">Terminate</a> <var>exitingWorker</var>.</li>
                  <li>Run the <a href="#update-state-algorithm">Update State</a> algorithm passing <var>exitingWorker</var> and <em>redundant</em> as the arguments.</li>
                </ol>
              </li>
            </ol>
          </li>
          <li>Run <a href="#activation-algorithm">Activate</a> algorithm, or its <a href="#dfn-processing-equivalence">equivalent</a>, passing <var>registration</var> as the argument.</li>
          <li>Abort these steps.</li>
        </ol>
      </li>
      <li>Pop the top element from <a href="#dfn-installation-result-handle-queue-adt">installation result handle queue</a>.</li>
      <li>Wait until no <a href="#dfn-service-worker-client">service worker client</a> is <a href="#dfn-use">using</a> <var>registration</var> or <var>registration</var>'s <a href="#dfn-waiting-worker">waiting worker</a>'s <a href="#dfn-skip-waiting-flag">skip waiting flag</a> is set.</li>
      <li>If <var>registration</var>'s <a href="#dfn-waiting-worker">waiting worker</a> <var>waitingWorker</var> is not null and <var>waitingWorker</var>'s <a href="#dfn-skip-waiting-flag">skip waiting flag</a> is not set, invoke <a href="#activation-algorithm">Activate</a> algorithm, or its <a href="#dfn-processing-equivalence">equivalent</a>, with <var>registration</var> as its argument.</li>
    </ol>
    </div>
  </section>

  <section title="activation-algorithm"><header><span class="section-number">9.5</span> <h3 id="activation-algorithm" data-bookmark-label="9.5 Activate">Activate</h3><span class="anchor"><a style="text-decoration: none;" href="#activation-algorithm">¶</a></span></header>


    <div class="algorithm">
    <dl>
      <dt>Input</dt>
        <dd><var>registration</var>, a <a href="#dfn-service-worker-registration">service worker registration</a></dd>
      <dt>Output</dt>
        <dd>None</dd>
    </dl>
    <ol>
      <li><a href="https://en.wikipedia.org/wiki/Timestamp-based_concurrency_control#Generating_a_Timestamp">Generate a timestamp</a> and let <var>timeStamp</var> be the result value.</li>
      <li>Push <var>timeStamp</var> to <a href="#dfn-activation-queue-adt">activation queue</a>.</li>
      <li><em>CheckPriority</em>: If the value of the top element of <a href="#dfn-activation-queue-adt">activation queue</a> is not <var>timeStamp</var>, then:
        <ol>
          <li>Wait until the top element of <a href="#dfn-activation-queue-adt">activation queue</a> is popped.</li>
          <li>Jump to the step labeled <em>CheckPriority</em>.</li>
        </ol>
        <p class="note"><em>Wait</em> is a blocking wait. Implementers may use a condition variable or its equivalent synchronization primitive.</p>
      </li>
      <li>Let <var>activatingWorker</var> be <var>registration</var>'s <a href="#dfn-waiting-worker">waiting worker</a>.</li>
      <li>Let <var>exitingWorker</var> be <var>registration</var>'s <a href="#dfn-active-worker">active worker</a>.</li>
      <li>If <var>activatingWorker</var> is null, then:
        <ol>
          <li>Pop the top element from <a href="#dfn-activation-queue-adt">activation queue</a>.</li>
          <li>Abort these steps.</li>
        </ol>
      </li>
      <li>If <var>exitingWorker</var> is not null, then:
        <ol>
          <li>Wait for <var>exitingWorker</var> to finish handling any in-progress requests.
          </li>
          <li><a href="https://html.spec.whatwg.org/multipage/workers.html#terminate-a-worker">Terminate</a> <var>exitingWorker</var>.</li>
          <li>Run the <a href="#update-state-algorithm">Update State</a> algorithm passing <var>exitingWorker</var> and <em>redundant</em> as the arguments.</li>
        </ol>
      </li>
      <li>Set <var>registration</var>'s <a href="#dfn-active-worker">active worker</a> to <var>activatingWorker</var>.</li>
      <li>Set <var>registration</var>'s <a href="#dfn-waiting-worker">waiting worker</a> to null.</li>
      <li>Run the <a href="#update-state-algorithm">Update State</a> algorithm passing <var>registration</var>'s <a href="#dfn-active-worker">active worker</a> and <em>activating</em> as the arguments.</li>
      <li>For each <a href="#dfn-service-worker-client">service worker client</a> <var>client</var> whose <a href="https://www.w3.org/Bugs/Public/show_bug.cgi?id=27146">creation url</a> <a href="#scope-match-algorithm">matches</a> <var>registration</var>'s <a href="#dfn-scope-url">scope url</a>:
        <ol>
          <li>If <var>client</var> is a <a href="#dfn-window-client">window client</a>, then:
            <ol>
              <li>Unassociate <var>client</var>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#responsible-document">responsible document</a> from its <a href="https://html.spec.whatwg.org/multipage/browsers.html#application-cache">application cache</a>, if it has one.</li>
            </ol>
          </li>
          <li>Else if <var>client</var> is a <a href="#dfn-sharedworker-client">shared worker client</a>, then:
            <ol>
              <li>Unassociate <var>client</var>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#global-object">global object</a> from its <a href="https://html.spec.whatwg.org/multipage/browsers.html#application-cache">application cache</a>, if it has one.</li>
            </ol>
          </li>
        </ol>
        <p class="note">Resources will now use the service worker registration instead of the existing application cache.</p>
      </li>
      <li>For each <a href="#dfn-service-worker-client">service worker client</a> <var>client</var> who is <a href="#dfn-use">using</a> <var>registration</var>:
        <ol>
          <li>Set <var>client</var>'s <a href="#dfn-active-worker">active worker</a> to <var>registration</var>'s <a href="#dfn-active-worker">active worker</a>.</li>
          <li>Invoke <a href="#notify-controller-change-algorithm">Notify Controller Change</a> algorithm with <var>client</var> as the argument.</li>
        </ol>
      </li>
      <li>Let <var>activeWorker</var> be <var>registration</var>'s <a href="#dfn-active-worker">active worker</a>.</li>
      <li>Invoke <a href="#run-service-worker-algorithm">Run Service Worker</a> algorithm with <var>activeWorker</var> as the arguement.</li>
      <li><a href="https://html.spec.whatwg.org/multipage/webappapis.html#queue-a-task">Queue a task</a> <var>task</var> to run the following substeps:
        <ol>
          <li>Create a <a href="https://html.spec.whatwg.org/#concept-events-trusted">trusted</a> event <var>e</var> that uses the <code><a href="#extendable-event-interface">ExtendableEvent</a></code> interface, with the event type <code><a href="#service-worker-global-scope-activate-event">activate</a></code>, which does not bubble, is not cancelable, and has no default action.</li>
          <li><a href="https://html.spec.whatwg.org/multipage/infrastructure.html#concept-event-dispatch">Dispatch</a> <var>e</var> at <var>activeWorker</var>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#environment-settings-object"> environment settings object</a>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#global-object">global object</a>.</li>
          <li>Let <var>extendLifetimePromises</var> be an empty array.</li>
          <li>For each <a href="https://dom.spec.whatwg.org/#concept-event-listener">event listener</a> <a href="https://dom.spec.whatwg.org/#concept-event-listener-invoke">invoked</a>:
            <ol>
              <li>If any uncaught runtime script error occurs, <a href="https://html.spec.whatwg.org/multipage/webappapis.html#report-the-error">report the error</a> for the script per the <a href="https://html.spec.whatwg.org/multipage/workers.html#runtime-script-errors-2">runtime script errors handling</a>.</li>
              <li>Let <var>eventObject</var> be the first argument passed to this <a href="https://dom.spec.whatwg.org/#concept-event-listener">event listener</a>.</li>
              <li>Append <var>eventObject</var>'s <a href="#dfn-extend-lifetime-promises">extend lifetime promises</a> to <var>extendLifetimePromises</var>.</li>
            </ol>
          </li>
          <li>Let <var>p</var> be <a href="http://www.w3.org/2001/tag/doc/promises-guide#waiting-for-all">waiting for all of</a> <var>extendLifetimePromises</var>.</li>
        </ol>
      </li>
      <li>Wait for <var>task</var> to have executed and <var>p</var> defined in <var>task</var> has settled, or <var>task</var> to have been discarded or the script to have been aborted by the <a href="https://html.spec.whatwg.org/multipage/workers.html#terminate-a-worker">termination</a> of <var>activeWorker</var>.</li>
      <li>Run the <a href="#update-state-algorithm">Update State</a> algorithm passing <var>registration</var>'s <a href="#dfn-active-worker">active worker</a> and <em>activated</em> as the arguments.</li>
      <li>Pop the top element from <a href="#dfn-activation-queue-adt">activation queue</a>.</li>
    </ol>
    </div>
  </section>

  <section title="run-service-worker-algorithm"><header><span class="section-number">9.6</span> <h3 id="run-service-worker-algorithm" data-bookmark-label="9.6 Run Service Worker">Run Service Worker</h3><span class="anchor"><a style="text-decoration: none;" href="#run-service-worker-algorithm">¶</a></span></header>


    <div class="algorithm">
    <dl>
      <dt>Input</dt>
        <dd><var>serviceWorker</var>, a <a href="#dfn-service-worker">service worker</a></dd>
      <dt>Output</dt>
        <dd>None</dd>
    </dl>
    <ol>
      <li>Assert: <var>serviceWorker</var> has the script resource successfully fetched against its <a href="#dfn-script-url">script url</a>.</li>
      <li>If <var>serviceWorker</var> is already running, abort these steps.</li>
      <li>Let <var>workerGlobalScope</var> be a new <code><a href="#service-worker-global-scope-interface">ServiceWorkerGlobalScope</a></code> object.</li>
      <!--li>Let <var>settingsObject</var> be the result of <a href="https://html.spec.whatwg.org/multipage/workers.html#set-up-a-worker-environment-settings-object">setting up a worker environment settings object</a> with <var>workerGlobalScope</var> and <var>serviceWorker</var>'s <a href="#dfn-script-url">script url</a>.</li-->
      <li>Let <var>workerEventLoop</var> be a newly created <a href="https://html.spec.whatwg.org/multipage/webappapis.html#event-loop">event loop</a>.</li>
      <li>Let <var>settingsObject</var> be a new <a href="https://html.spec.whatwg.org/multipage/webappapis.html#environment-settings-object">environment settings object</a> whose algorithms are defined as follows:
        <dl>
          <dt>The <a href="https://html.spec.whatwg.org/multipage/webappapis.html#script-execution-environment">script execution environments</a></dt>
          <dd>When the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#environment-settings-object">environment settings object</a> is created, for each language supported by the user agent, create an appropriate execution environment as defined by the relevant specification.</dd>
          <dd>When a <a href="https://html.spec.whatwg.org/multipage/webappapis.html#script-execution-environment">script execution environment</a> is needed, return the appropriate one from those created when the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#environment-settings-object">environment settings object</a> was created.</dd>
          <dt>The <a href="https://html.spec.whatwg.org/multipage/webappapis.html#global-object">global object</a></dt>
          <dd>Return <var>workerGlobalScope</var>.</dd>
          <dt>The <a href="https://html.spec.whatwg.org/multipage/webappapis.html#responsible-event-loop">responsible event loop</a></dt>
          <dd>Return <var>workerEventLoop</var>.</dd>
          <dt>The <a href="https://html.spec.whatwg.org/multipage/webappapis.html#referrer-source">referrer source</a></dt>
          <dd>Return <var>serviceWorker</var>'s <a href="#dfn-script-url">script url</a>.</dd>
          <dt>The <a href="https://html.spec.whatwg.org/multipage/webappapis.html#api-url-character-encoding">API URL character encoding</a></dt>
          <dd>Return UTF-8.</dd>
          <dt>The <a href="https://html.spec.whatwg.org/multipage/webappapis.html#api-base-url">API base URL</a></dt>
          <dd>Return <var>serviceWorker</var>'s <a href="#dfn-script-url">script url</a>.</dd>
          <dt>The <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a> and <a href="https://html.spec.whatwg.org/multipage/browsers.html#effective-script-origin">effective script origin</a></dt>
          <dd>Return its registering <a href="#dfn-service-worker-client">service worker client</a>'s <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a>.</dd>
        </dl>
      </li>
      <li>Create a separate parallel execution environment (i.e. a separate thread or process or equivalent construct), and run the rest of these steps in that context.</li>
      <li>Let <var>source</var> be the result of running the <a href="https://html.spec.whatwg.org/multipage/infrastructure.html#utf-8-decode">UTF-8 decode</a> algorithm on the script resource of <var>serviceWorker</var>.</li>
      <li>Let <var>language</var> be JavaScript.</li>
      <li>In the newly created execution environment, create a <a href="https://html.spec.whatwg.org/multipage/infrastructure.html#javascript-global-environment">JavaScript global environment</a> whose <em>global object</em> is <var>workerGlobalScope</var>. (The <a href="https://html.spec.whatwg.org/multipage/infrastructure.html#javascript-global-environment">JavaScript global environment</a> whose <em>global object</em> is a <code><a href="#service-worker-global-scope-interface">ServiceWorkerGlobalScope</a></code> object is defined as the <dfn id="service-worker-environment">service worker environment</dfn>, which is a type of <a href="https://html.spec.whatwg.org/multipage/webappapis.html#worker-environment">worker environments</a>.)</li>
      <li>Let <var>script</var> be a new <a href="https://html.spec.whatwg.org/multipage/webappapis.html#concept-script">script</a>.</li>
      <li>Obtain the appropriate <a href="https://html.spec.whatwg.org/multipage/webappapis.html#script-execution-environment">script execution environment</a> for the scripting language <var>language</var> from <var>settingsObject</var>.</li>
      <li>Parse/compile/initialize <var>source</var> using that <a href="https://html.spec.whatwg.org/multipage/webappapis.html#script-execution-environment">script execution environment</a>, as appropriate for <var>language</var>, and thus obtain a <a href="https://html.spec.whatwg.org/multipage/webappapis.html#code-entry-point">code entry-point</a>. If the script was not compiled successfully, let the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#code-entry-point">code entry-point</a> be a no-op script, and act as if a corresponding uncaught script error had occurred.</li>
      <li>Let <var>script</var>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#settings-object">settings object</a> be <var>settingsObject</var>.</li>
      <li><a href="https://html.spec.whatwg.org/multipage/webappapis.html#jump-to-a-code-entry-point">Jump</a> to the <var>script</var>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#code-entry-point">code entry-point</a>, and let that run until it either returns, fails to catch an exception, or gets aborted by the <a href="https://html.spec.whatwg.org/multipage/workers.html#kill-a-worker">kill a worker</a> or <a href="https://html.spec.whatwg.org/multipage/workers.html#terminate-a-worker">terminate a worker</a> algorithms.</li>
      <li>Run the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#responsible-event-loop">responsible event loop</a> specified by <var>settingsObject</var> until it is destroyed.</li>
      <li>Empty <var>workerGlobalScope</var>'s <a href="">list of active timers</a>.</li>
    </ol>
    </div>
  </section>

  <section title="on-fetch-request-algorithm"><header><span class="section-number">9.7</span> <h3 id="on-fetch-request-algorithm" data-bookmark-label="9.7 Handle Fetch">Handle Fetch</h3><span class="anchor"><a style="text-decoration: none;" href="#on-fetch-request-algorithm">¶</a></span></header>


    <p id="on-fetch-request-algorithm.1">The <a href="#on-fetch-request-algorithm">Handle Fetch</a> algorithm is the entry point for the <a href="https://fetch.spec.whatwg.org/#concept-fetch">fetch</a> handling handed to the <a href="#dfn-service-worker">service worker</a> context.</p>

    <div class="algorithm">
    <dl>
      <dt>Input</dt>
        <dd><var>request</var>, a <a href="https://fetch.spec.whatwg.org/#concept-request">request</a></dd>
      <dt>Output</dt>
        <dd><var>response</var>, a <a href="https://fetch.spec.whatwg.org/#concept-response">response</a></dd>
    </dl>
    <ol>
      <li>Let <var>handleFetchFailed</var> be false.</li>
      <li>Let <var>respondWithEntered</var> be false.</li>
      <li>Let <var>eventCanceled</var> be false.</li>
      <li>Let <var>r</var> be a new <code><a href="https://fetch.spec.whatwg.org/#request">Request</a></code> object associated with <var>request</var>.</li>
      <li>Let <var>headersObject</var> be <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#dom-request-headers">headers</a> attribute value.</li>
      <li>Set <var>headersObject</var>'s <a href="https://fetch.spec.whatwg.org/#concept-headers-guard">guard</a> to <em>immutable</em>.</li>
      <li>Let <var>response</var> be null.</li>
      <li>Let <var>registration</var> be null.</li>
      <li>Let <var>client</var> be <var>request</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-client">client</a>.</li>
      <li>Assert: <var>request</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-context">context</a> is not "<code>serviceworker</code>".</li>
      <li>If <var>request</var> is a <a href="https://fetch.spec.whatwg.org/#potential-client-request">potential client request</a>, then:
        <ol>
          <li>Return null.</li>
        </ol>
      </li>
      <li>Else if <var>request</var> is a <a href="https://fetch.spec.whatwg.org/#client-request">client request</a>, then:
        <p class="note">If the client request is under the scope of a service worker registration, appplication cache is completely bypassed regardless of whether the client request uses the service worker registration.</p>
        <p class="fixme">This behavior requires changing the algorithm steps in HTML: <a href="https://www.w3.org/Bugs/Public/show_bug.cgi?id=27482">Issue 27482</a>.</p>
        <ol>
          <li>If the <a href="https://html.spec.whatwg.org/multipage/browsers.html#navigate">navigation</a> triggering <var>request</var> was initiated with a shift+reload or equivalent, then:
            <ol>
              <li>Return null.</li>
            </ol>
          </li>
          <li>If <var>request</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-context">context</a> is "<code>iframe</code>" and <var>request</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-url">url</a> <a href="https://url.spec.whatwg.org/#is-local">is local</a>, then:
            <ol>
              <li>If <var>client</var>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#responsible-browsing-context">responsible browsing context</a>'s <a href="https://html.spec.whatwg.org/multipage/browsers.html#parent-browsing-context">parent browsing context</a>'s <a href="https://html.spec.whatwg.org/multipage/browsers.html#window">Window</a> object's <a href="#dfn-service-worker-client">service worker client</a>'s <a href="#dfn-service-worker-client-active-worker">active worker</a> <var>activeWorker</var> is not null, set <var>registration</var> to <var>activeWorker</var>'s <a href="#dfn-containing-service-worker-registration">containing service worker registration</a>.</li>
            </ol>
          </li>
          <li>Else:
            <ol>
              <li>Set <var>registration</var> to the result of running <a href="#scope-match-algorithm">Match Service Worker Registration</a> algorithm, or its <a href="#dfn-processing-equivalence">equivalent</a>, passing <var>request</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-url">url</a> as the argument.</li>
            </ol>
          </li>
          <li>If <var>registration</var> is null or <var>registration</var>'s <a href="#dfn-active-worker">active worker</a> is null, return null.</li>
          <li>Set <var>client</var>'s <a href="#dfn-service-worker-client-active-worker">active worker</a> to <var>registration</var>'s <a href="#dfn-active-worker">active worker</a>.</li>
        </ol>
        <p class="note">From this point, the <a href="#dfn-service-worker-client">service worker client</a> starts to <a href="#dfn-use">use</a> its <a href="#dfn-service-worker-client-active-worker">active worker</a>'s <a href="#dfn-containing-service-worker-registration">containing service worker registration</a>.</p>
      </li>
      <li>Else if <var>request</var> is a <a href="https://fetch.spec.whatwg.org/#resource-request">resource request</a>, then:
        <ol>
          <li>If <var>client</var>'s <a href="#dfn-service-worker-client-active-worker">active worker</a> is non-null, then:
            <ol>
              <li>Set <var>registration</var> to <var>client</var>'s <a href="#dfn-service-worker-client-active-worker">active worker</a>'s <a href="#dfn-containing-service-worker-registration">containing service worker registration</a>.</li>
            </ol>
          </li>
          <li>Else:
            <ol>
              <li>Return null.</li>
            </ol>
          </li>
        </ol>
      </li>
      <li>Let <var>activeWorker</var> be <var>registration</var>'s <a href="#dfn-active-worker">active worker</a>.</li>
      <li>If <var>activeWorker</var>'s <a href="#dfn-state">state</a> is <em>activating</em>, then:
        <ol>
          <li>Wait for <var>activeWorker</var>'s <a href="#dfn-state">state</a> to become <em>activated</em>.</li>
        </ol>
      </li>
      <li><a href="http://www.ecma-international.org/ecma-262/6.0/#sec-algorithm-conventions">Assert</a>: <var>activeWorker</var> is not null, and its <a href="#dfn-state">state</a> is <em>activated</em>.</li>
      <li>Invoke <a href="#run-service-worker-algorithm">Run Service Worker</a> algorithm with <var>activeWorker</var> as the arguement.</li>
      <li><a href="https://html.spec.whatwg.org/multipage/webappapis.html#queue-a-task">Queue a task</a> <var>task</var> to run the following substeps:
        <ol>
          <li>Create a <a href="https://html.spec.whatwg.org/#concept-events-trusted">trusted</a> event <var>e</var> that uses the <code><a href="#fetch-event-interface">FetchEvent</a></code> interface, with the event type <code><a href="#service-worker-global-scope-fetch-event">fetch</a></code>, which does not bubble, is not cancelable, and has no default action.</li>
          <li>Let the <a href="#fetch-event-request-attribute">request</a> attribute of <var>e</var> be initialized to <var>r</var>.</li>
          <li>Let <var>c</var> be null.</li>
          <li>If <var>request</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-client">client</a> is a <a href="#dfn-window-client">window client</a>, set <var>c</var> to the result of running <a href="#capture-windowclient-algorithm">Capture Window Client</a> algorithm, or its <a href="#dfn-processing-equivalence">equivalent</a>, with <var>request</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-client">client</a>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#responsible-browsing-context">responsible browsing context</a> as the argument.</li>
          <li>Else, set <var>c</var> to a <code><a href="#client-interface">Client</a></code> object that represents <var>request</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-client">client</a>.</li>
          <li>Let the <a href="#fetch-event-client-attribute">client</a> attribute of <var>e</var> be initialized to <var>c</var>.</li>
          <li>Let the <a href="#fetch-event-isreload-attribute">isReload</a> attribute of <var>e</var> be initialized to <code>true</code> if <var>request</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-client">client</a> is a <a href="#dfn-window-client">window client</a> and the event was dispatched with the user's intention for the page reload, and <code>false</code> otherwise.</li>
          <li><a href="https://html.spec.whatwg.org/multipage/infrastructure.html#concept-event-dispatch">Dispatch</a> <var>e</var> at <var>activeWorker</var>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#environment-settings-object"> environment settings object</a>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#global-object">global object</a>.</li>
          <li>For each <a href="https://dom.spec.whatwg.org/#concept-event-listener">event listener</a> <a href="https://dom.spec.whatwg.org/#concept-event-listener-invoke">invoked</a>:
            <ol>
              <li>If any uncaught runtime script error occurs, then:
                <ol>
                  <li><a href="https://html.spec.whatwg.org/multipage/webappapis.html#report-the-error">Report the error</a> for the script per the <a href="https://html.spec.whatwg.org/multipage/workers.html#runtime-script-errors-2">runtime script errors handling</a>.</li>
                  <li>Abort these steps.</li>
                </ol>
              </li>
              <li>Let <var>event</var> be the event for which this <a href="https://dom.spec.whatwg.org/#concept-event-listener">event listener</a> was invoked.</li>
              <li>If <var>event</var>'s <a href="#respond-with-entered-flag">respond-with entered flag</a> is set, then:
                <ol>
                  <li>Set <var>respondWithEntered</var> to true.</li>
                </ol>
              </li>
              <li>If <var>event</var>'s <a href="#wait-to-respond-flag">wait to respond flag</a> is set, then:
                <ol>
                  <li>Wait until <var>event</var>'s <a href="#wait-to-respond-flag">wait to respond flag</a> is unset.</li>
                  <li>If <var>event</var>'s <a href="#respond-with-error-flag">respond-with error flag</a> is set, then:
                    <ol>
                      <li>Set <var>handleFetchFailed</var> to true.</li>
                    </ol>
                  </li>
                  <li>Else:
                    <ol>
                      <li>If the argument passed into the <var>event</var>'s <code><a href="#fetch-event-respondwith-method">respondWith(<var>r</var>)</a></code> method <var>arg</var> is a <code><a href="https://fetch.spec.whatwg.org/#response">Response</a></code> object, then:
                        <ol><li>Set <var>response</var> to <var>arg</var>.</li></ol>
                      </li>
                      <li>Else:
                        <ol>
                          <li>Set <var>response</var> to the value which <var>arg</var> resolved with.</li>
                        </ol>
                      </li>
                    </ol>
                  </li>
                </ol>
              </li>
              <li>If <var>event</var>'s <a href="https://dom.spec.whatwg.org/#canceled-flag">canceled flag</a> is set, then:
                <ol>
                  <li>Set <var>eventCanceled</var> to true.</li>
                </ol>
              </li>
            </ol>
          </li>
        </ol>
        <p>If <var>task</var> is discarded or the script has been aborted by the <a href="https://html.spec.whatwg.org/multipage/workers.html#terminate-a-worker">termination</a> of <var>activeWorker</var>, set <var>handleFetchFailed</var> to true.</p>
      </li>
      <li>Wait for <var>task</var> to have executed or been discarded.</li>
      <li>If <var>respondWithEntered</var> is false, then:
        <ol>
          <li>If <var>eventCanceled</var> is true, then:
            <ol>
              <li>Return a <a href="https://fetch.spec.whatwg.org/#concept-network-error">network error</a> and run the following substeps in parallel.</li>
            </ol>
          </li>
          <li>Else:
            <ol>
              <li>Return null and run the following substeps in parallel.</li>
            </ol>
          </li>
          <li>If <var>request</var> is a <a href="https://fetch.spec.whatwg.org/#client-request">client request</a>, then:
            <ol>
              <li>Invoke <a href="#soft-update-algorithm">Soft Update</a> algorithm, or its <a href="#dfn-processing-equivalence">equivalent</a>, with <var>registration</var>.</li>
            </ol>
          </li>
          <li>Abort these steps.</li>
        </ol>
      </li>
      <li>If <var>handleFetchFailed</var> is true, then:
        <ol>
          <li>Return a <a href="https://fetch.spec.whatwg.org/#concept-network-error">network error</a> and run the following substeps in parallel.</li>
          <li>If <var>request</var> is a <a href="https://fetch.spec.whatwg.org/#client-request">client request</a>, then:
            <ol>
              <li>Invoke <a href="#soft-update-algorithm">Soft Update</a> algorithm, or its <a href="#dfn-processing-equivalence">equivalent</a>, with <var>registration</var>.</li>
            </ol>
          </li>
        </ol>
      </li>
      <li>Else:
        <ol>
          <li>Return a <a href="https://fetch.spec.whatwg.org/#concept-response">response</a> represented by <var>response</var> and run the following substeps in parallel.</li>
          <li>If <var>request</var> is a <a href="https://fetch.spec.whatwg.org/#client-request">client request</a>, then:
            <ol>
              <li>Invoke <a href="#soft-update-algorithm">Soft Update</a> algorithm, or its <a href="#dfn-processing-equivalence">equivalent</a>, with <var>registration</var>.</li>
            </ol>
          </li>
        </ol>
      </li>
    </ol>
    </div>
  </section>

  <section title="handle-functional-event-algorithm"><header><span class="section-number">9.8</span> <h3 id="handle-functional-event-algorithm" data-bookmark-label="9.8 Handle Functional Event">Handle Functional Event</h3><span class="anchor"><a style="text-decoration: none;" href="#handle-functional-event-algorithm">¶</a></span></header>


    <div class="algorithm">
    <dl>
    <dt>Input</dt>
        <dd><var>registration</var>, a <a href="#dfn-service-worker-registration">service worker registration</a></dd>
        <dd><var>callbackSteps</var>, an algorithm</dd>
    <dt>Output</dt>
        <dd>None</dd>
    </dl>
    <ol>
      <li><a href="http://www.ecma-international.org/ecma-262/6.0/#sec-algorithm-conventions">Assert</a>: a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-list-and-record-specification-type">Record</a> with the [[value]] equals to <var>registration</var> is contained in <a href="#dfn-scope-to-registration-map">scope to registration map</a>.</li>
      <li><a href="http://www.ecma-international.org/ecma-262/6.0/#sec-algorithm-conventions">Assert</a>: <var>registration</var>'s <a href="#dfn-active-worker">active worker</a> is not null.</li>
      <li>Let <var>activeWorker</var> be <var>registration</var>'s <a href="#dfn-active-worker">active worker</a>.</li>
      <li>Invoke <a href="#run-service-worker-algorithm">Run Service Worker</a> algorithm with <var>activeWorker</var> as the arguement.</li>
      <li><a href="https://html.spec.whatwg.org/multipage/webappapis.html#queue-a-task">Queue a task</a> to invoke <var>callbackSteps</var> with <var>activeWorker</var>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#environment-settings-object"> environment settings object</a>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#global-object">global object</a> as its argument.
        <p>The <a href="https://html.spec.whatwg.org/multipage/webappapis.html#concept-task">task</a> <em class="rfc2119" title="MUST">must</em> use the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#dom-manipulation-task-source">DOM manipulation task source</a>.</p>
      </li>
    </ol>
    </div>
  </section>

  <section title="on-client-unload-algorithm"><header><span class="section-number">9.9</span> <h3 id="on-client-unload-algorithm" data-bookmark-label="9.9 Handle Service Worker Client Unload">Handle Service Worker Client Unload</h3><span class="anchor"><a style="text-decoration: none;" href="#on-client-unload-algorithm">¶</a></span></header>


    <p id="on-client-unload-algorithm.1">The user agent <em class="rfc2119" title="MUST">must</em> run these steps, or their <a href="#dfn-processing-equivalence">equivalent</a>, when a <a href="#dfn-service-worker-client">service worker client</a> unloads by <a href="https://html.spec.whatwg.org/multipage/browsers.html#unload-a-document">unloading</a>, <a href="https://html.spec.whatwg.org/multipage/workers.html#kill-a-worker">being killed</a>, or <a href="https://html.spec.whatwg.org/multipage/workers.html#terminate-a-worker">terminating</a>.</p>

    <div class="algorithm">
    <dl>
    <dt>Input</dt>
        <dd><var>client</var>, a <a href="#dfn-service-worker-client">service worker client</a></dd>
    <dt>Output</dt>
        <dd>None</dd>
    </dl>
    <ol>
      <li>Run the following steps atomically.</li>
      <li>Let <var>registration</var> be the <a href="#dfn-service-worker-registration">service worker registration</a> <a href="#dfn-use">used</a> by <var>client</var>.</li>
      <li>If <var>registration</var> is null, then:
        <ol>
          <li>Abort these steps.</li>
        </ol>
      </li>
      <li>If any other <a href="#dfn-service-worker-client">service worker client</a> is <a href="#dfn-use">using</a> <var>registration</var>, then:
        <ol>
          <li>Abort these steps.</li>
        </ol>
      </li>
      <li>If <var>registration</var>'s <a href="#dfn-uninstalling-flag">uninstalling flag</a> is true, then:
        <ol>
          <li>Invoke <a href="#clear-registration-algorithm">Clear Registration</a> algorithm passing <var>registration</var> as its argument.</li>
          <li>Abort these steps.</li>
        </ol>
      </li>
      <li>If <var>registration</var>'s <a href="#dfn-waiting-worker">waiting worker</a> is not null:
        <ol>
          <li>Run <a href="#activation-algorithm">Activate</a> algorithm, or its <a href="#dfn-processing-equivalence">equivalent</a>, with <var>registration</var> at the argument.</li>
        </ol>
      </li>
    </ol>
    </div>
  </section>

  <section title="unregister-algorithm"><header><span class="section-number">9.10</span> <h3 id="unregister-algorithm" data-bookmark-label="9.10 Unregister">Unregister</h3><span class="anchor"><a style="text-decoration: none;" href="#unregister-algorithm">¶</a></span></header>


    <div class="algorithm">
    <dl>
      <dt>Input</dt>
        <dd><var>client</var>, a <a href="#dfn-service-worker-client">service worker client</a></dd>
        <dd><var>scope</var>, an <a href="https://url.spec.whatwg.org/#concept-absolute-url">absolute URL</a></dd>
      <dt>Output</dt>
        <dd><var>promise</var>, a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a></dd>
    </dl>
    <ol>
      <li>Let <var>promise</var> be a new <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a>.</li>
      <li>Run the following substeps in parallel:
        <ol>
          <li>If the <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a> of <var>scope</var> is not <var>client</var>'s <a href="https://html.spec.whatwg.org/multipage/browsers.html#origin-2">origin</a>, then:
            <ol>
              <li>Reject <var>promise</var> with a "<code><a href="http://heycam.github.io/webidl/#securityerror">SecurityError</a></code>" exception.</li>
              <li>Abort these steps.</li>
            </ol>
          </li>
          <li>Let <var>registration</var> be the result of running <a href="#get-registration-algorithm">Get Registration</a> algorithm passing <var>scope</var> as the argument.</li>
          <li>If <var>registration</var> is null, then:
            <ol>
              <li>Resolve <var>promise</var> with false.</li>
              <li>Abort these steps.</li>
            </ol>
          </li>
          <li>Set <var>registration</var>'s <a href="#dfn-uninstalling-flag">uninstalling flag</a>.</li>
          <li>Resolve <var>promise</var> with true.</li>
          <li>If no <a href="#dfn-service-worker-client">service worker client</a> is <a href="#dfn-use">using</a> <var>registration</var>, then:
            <ol>
              <li>If <var>registration</var>'s <a href="#dfn-uninstalling-flag">uninstalling flag</a> is unset, then:
                <ol>
                  <li>Abort these steps.</li>
                </ol>
              </li>
              <li>Invoke <a href="#clear-registration-algorithm">Clear Registration</a> algorithm passing <var>registration</var> as its argument.</li>
            </ol>
          </li>
        </ol>
      </li>
      <li>Return <var>promise</var>.</li>
    </ol>
    </div>
  </section>

  <section title="set-registration-algorithm"><header><span class="section-number">9.11</span> <h3 id="set-registration-algorithm" data-bookmark-label="9.11 Set Registration">Set Registration</h3><span class="anchor"><a style="text-decoration: none;" href="#set-registration-algorithm">¶</a></span></header>


    <div class="algorithm">
    <dl>
      <dt>Input</dt>
        <dd><var>scope</var>, an <a href="https://url.spec.whatwg.org/#concept-absolute-url">absolute URL</a></dd>
      <dt>Output</dt>
        <dd><var>registration</var>, a <a href="#dfn-service-worker-registration">service worker registration</a></dd>
    </dl>
    <ol>
      <li>Run the following steps atomically.</li>
      <li>Let <var>scopeString</var> be <a href="https://url.spec.whatwg.org/#concept-url-serializer">serialized</a> <var>scope</var> with the <em>exclude fragment flag</em> set.</li>
      <li>Let <var>registration</var> be a new <a href="#dfn-service-worker-registration">service worker registration</a> whose <a href="#dfn-scope-url">scope url</a> is set to <var>scope</var>.</li>
      <li>Set a newly-created <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-list-and-record-specification-type">Record</a> {[[key]]: <var>scopeString</var>, [[value]]: <var>registration</var>} to <a href="#dfn-scope-to-registration-map">scope to registration map</a>.</li>
      <li>Return <var>registration</var>.</li>
    </ol>
    </div>
  </section>

  <section title="clear-registration-algorithm"><header><span class="section-number">9.12</span> <h3 id="clear-registration-algorithm" data-bookmark-label="9.12 Clear Registration">Clear Registration</h3><span class="anchor"><a style="text-decoration: none;" href="#clear-registration-algorithm">¶</a></span></header>


    <div class="algorithm">
    <dl>
      <dt>Input</dt>
        <dd><var>registration</var>, a <a href="#dfn-service-worker-registration">service worker registration</a></dd>
      <dt>Output</dt>
        <dd>None</dd>
    </dl>
    <ol>
      <li>Run the following steps atomically.</li>
      <li>If <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a> is not null, then:
        <ol>
          <li><a href="https://html.spec.whatwg.org/multipage/workers.html#terminate-a-worker">Terminate</a> <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a>.</li>
          <li>Run the <a href="#update-state-algorithm">Update State</a> algorithm passing <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a> and <em>redundant</em> as the arguments.</li>
          <li>Set <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a> to null.</li>
          <li>The user agent <em class="rfc2119" title="MAY">may</em> abort in-flight requests triggered by <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a>.</li>
        </ol>
      </li>
      <li>If <var>registration</var>'s <a href="#dfn-waiting-worker">waiting worker</a> is not null, then:
        <ol>
          <li><a href="https://html.spec.whatwg.org/multipage/workers.html#terminate-a-worker">Terminate</a> <var>registration</var>'s <a href="#dfn-waiting-worker">waiting worker</a>.</li>
          <li>Run the <a href="#update-state-algorithm">Update State</a> algorithm passing <var>registration</var>'s <a href="#dfn-waiting-worker">waiting worker</a> and <em>redundant</em> as the arguments.</li>
          <li>Set <var>registration</var>'s <a href="#dfn-waiting-worker">waiting worker</a> to null.</li>
          <li>The user agent <em class="rfc2119" title="MAY">may</em> abort in-flight requests triggered by <var>registration</var>'s <a href="#dfn-waiting-worker">waiting worker</a>.</li>
        </ol>
      </li>
      <li>If <var>registration</var>'s <a href="#dfn-active-worker">active worker</a> is not null, then:
        <ol>
          <li><a href="https://html.spec.whatwg.org/multipage/workers.html#terminate-a-worker">Terminate</a> <var>registration</var>'s <a href="#dfn-active-worker">active worker</a>.</li>
          <li>Run the <a href="#update-state-algorithm">Update State</a> algorithm passing <var>registration</var>'s <a href="#dfn-active-worker">active worker</a> and <em>redundant</em> as the arguments.</li>
          <li>Set <var>registration</var>'s <a href="#dfn-active-worker">active worker</a> to null.</li>
          <li>The user agent <em class="rfc2119" title="MAY">may</em> abort in-flight requests triggered by <var>registration</var>'s <a href="#dfn-active-worker">active worker</a>.</li>
        </ol>
      </li>
      <li>Delete a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-list-and-record-specification-type">Record</a> {[[key]], [[value]]} <var>entry</var> of its <a href="#dfn-scope-to-registration-map">scope to registration map</a> where <var>registration</var>'s <a href="#dfn-scope-url">scope url</a> matches <var>entry</var>.[[key]].</li>
    </ol>
    </div>
  </section>

  <section title="update-state-algorithm"><header><span class="section-number">9.13</span> <h3 id="update-state-algorithm" data-bookmark-label="9.13 Update State">Update State</h3><span class="anchor"><a style="text-decoration: none;" href="#update-state-algorithm">¶</a></span></header>


    <div class="algorithm">
    <dl>
      <dt>Input</dt>
        <dd><var>worker</var>, a <a href="#dfn-service-worker">service worker</a></dd>
        <dd><var>state</var>, a <a href="#dfn-service-worker">service worker</a>'s <a href="#dfn-state">state</a></dd>
      <dt>Output</dt>
        <dd>None</dd>
    </dl>
    <ol>
      <li>Set <var>worker</var>'s <a href="#dfn-state">state</a> to <var>state</var>.</li>
      <li>Let <var>serviceWorkers</var> be an array containing all the <code><a href="#service-worker-interface">ServiceWorker</a></code> objects associated with <var>worker</var>.</li>
      <li>For each <var>serviceWorker</var> in <var>serviceWorkers</var>:
        <ol>
          <li><a href="https://html.spec.whatwg.org/multipage/webappapis.html#queue-a-task">Queue a task</a> to <a href="https://html.spec.whatwg.org/#fire-a-simple-event">fire a simple event named</a> <code>statechange</code> at <var>serviceWorker</var>.</li>
        </ol>
        <p>The <a href="https://html.spec.whatwg.org/multipage/webappapis.html#concept-task">task</a> <em class="rfc2119" title="MUST">must</em> use <var>serviceWorker</var>'s <a href="#dfn-service-worker-interface-client">service worker client</a>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#responsible-event-loop">responsible event loop</a> and the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#dom-manipulation-task-source">DOM manipulation task source</a>.</p>
      </li>
    </ol>
    </div>
  </section>

  <section title="notify-controller-change-algorithm"><header><span class="section-number">9.14</span> <h3 id="notify-controller-change-algorithm" data-bookmark-label="9.14 Notify Controller Change">Notify Controller Change</h3><span class="anchor"><a style="text-decoration: none;" href="#notify-controller-change-algorithm">¶</a></span></header>


    <div class="algorithm">
    <dl>
      <dt>Input</dt>
        <dd><var>client</var>, a <a href="#dfn-service-worker-client">service worker client</a></dd>
      <dt>Output</dt>
        <dd>None</dd>
    </dl>
    <ol>
      <li><a href="http://www.ecma-international.org/ecma-262/6.0/#sec-algorithm-conventions">Assert</a>: <var>client</var> is not null.</li>
      <li><a href="https://html.spec.whatwg.org/multipage/webappapis.html#queue-a-task">Queue a task</a> to <a href="https://html.spec.whatwg.org/#fire-a-simple-event">fire a simple event named</a> <code>controllerchange</code> at the <code><a href="#service-worker-container-interface">ServiceWorkerContainer</a></code> object <var>client</var> is <a href="#dfn-service-worker-container-interface-client">associated</a> with.</li>
    </ol>
    <p>The <a href="https://html.spec.whatwg.org/multipage/webappapis.html#concept-task">task</a> <em class="rfc2119" title="MUST">must</em> use <var>client</var>'s <a href="https://html.spec.whatwg.org/multipage/webappapis.html#responsible-event-loop">responsible event loop</a> and the <a href="https://html.spec.whatwg.org/multipage/webappapis.html#dom-manipulation-task-source">DOM manipulation task source</a>.</p>
    </div>
  </section>

  <section title="scope-match-algorithm"><header><span class="section-number">9.15</span> <h3 id="scope-match-algorithm" data-bookmark-label="9.15 Match Service Worker Registration">Match Service Worker Registration</h3><span class="anchor"><a style="text-decoration: none;" href="#scope-match-algorithm">¶</a></span></header>


    <div class="algorithm">
    <dl>
      <dt>Input</dt>
        <dd><var>clientURL</var>, an <a href="https://url.spec.whatwg.org/#concept-absolute-url">absolute URL</a></dd>
      <dt>Output</dt>
        <dd><var>registration</var>, a <a href="#dfn-service-worker-registration">service worker registration</a></dd>
    </dl>
    <ol>
      <li>Run the following steps atomically.</li>
      <li>Let <var>clientURLString</var> be <a href="https://url.spec.whatwg.org/#concept-url-serializer">serialized</a> <var>clientURL</var>.</li>
      <li>Let <var>matchingScope</var> be the longest [[key]] in <a href="#dfn-scope-to-registration-map">scope to registration map</a> starting with the value of <var>clientURLString</var>.</li>
      <li>Let <var>matchingScopeURL</var> be the result of <a href="https://url.spec.whatwg.org/#concept-url-parser">parsing</a> <var>matchingScope</var>.</li>
      <li>Let <var>registration</var> be the result of running <a href="#get-registration-algorithm">Get Registration</a> algorithm passing <var>matchingScopeURL</var> as the argument.</li>
      <li>If <var>registration</var> is not null and <var>registration</var>'s <a href="#dfn-uninstalling-flag">uninstalling flag</a> is set, then:
        <ol>
          <li>Return null.</li>
        </ol>
      </li>
      <li>Return <var>registration</var>.</li>
    </ol>
    </div>
  </section>

  <section title="get-registration-algorithm"><header><span class="section-number">9.16</span> <h3 id="get-registration-algorithm" data-bookmark-label="9.16 Get Registration">Get Registration</h3><span class="anchor"><a style="text-decoration: none;" href="#get-registration-algorithm">¶</a></span></header>


    <div class="algorithm">
    <dl>
      <dt>Input</dt>
        <dd><var>scope</var>, an <a href="https://url.spec.whatwg.org/#concept-absolute-url">absolute URL</a></dd>
      <dt>Output</dt>
        <dd><var>registration</var>, a <a href="#dfn-service-worker-registration">service worker registration</a></dd>
    </dl>
    <ol>
      <li>Run the following steps atomically.</li>
      <li>Let <var>registration</var> be null.</li>
      <li>Let <var>scopeString</var> be <a href="https://url.spec.whatwg.org/#concept-url-serializer">serialized</a> <var>scope</var> with the <em>exclude fragment flag</em> set.</li>
      <li>For each <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-list-and-record-specification-type">Record</a> {[[key]], [[value]]} <var>entry</var> of its <a href="#dfn-scope-to-registration-map">scope to registration map</a>:
        <ol>
          <li>If <var>scopeString</var> matches <var>entry</var>.[[key]], then:
            <ol>
              <li>Set <var>registration</var> to <var>entry</var>.[[value]].</li>
            </ol>
          </li>
        </ol>
      </li>
      <li>Return <var>registration</var>.</li>
    </ol>
    </div>
  </section>

  <section title="get-newest-worker-algorithm"><header><span class="section-number">9.17</span> <h3 id="get-newest-worker-algorithm" data-bookmark-label="9.17 Get Newest Worker">Get Newest Worker</h3><span class="anchor"><a style="text-decoration: none;" href="#get-newest-worker-algorithm">¶</a></span></header>


    <div class="algorithm">
    <dl>
      <dt>Input</dt>
        <dd><var>registration</var>, a <a href="#dfn-service-worker-registration">service worker registration</a></dd>
      <dt>Output</dt>
        <dd><var>worker</var>, a <a href="#dfn-service-worker">service worker</a></dd>
    </dl>
    <ol>
      <li>Run the following steps atomically.</li>
      <li>Let <var>newestWorker</var> be null.</li>
      <li>If <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a> is not null, then:
        <ol>
          <li>Set <var>newestWorker</var> to <var>registration</var>'s <a href="#dfn-installing-worker">installing worker</a>.</li>
        </ol>
      </li>
      <li>Else if <var>registration</var>'s <a href="#dfn-waiting-worker">waiting worker</a> is not null, then:
        <ol>
          <li>Set <var>newestWorker</var> to <var>registration</var>'s <a href="#dfn-waiting-worker">waiting worker</a>.</li>
        </ol>
      </li>
      <li>Else if <var>registration</var>'s <a href="#dfn-active-worker">active worker</a> is not null, then:
        <ol>
          <li>Set <var>newestWorker</var> to <var>registration</var>'s <a href="#dfn-active-worker">active worker</a>.</li>
        </ol>
      </li>
      <li>Return <var>newestWorker</var>.</li>
    </ol>
    </div>
  </section>

  <section title="capture-windowclient-algorithm"><header><span class="section-number">9.18</span> <h3 id="capture-windowclient-algorithm" data-bookmark-label="9.18 Capture Window Client">Capture Window Client</h3><span class="anchor"><a style="text-decoration: none;" href="#capture-windowclient-algorithm">¶</a></span></header>


    <div class="algorithm">
    <dl>
      <dt>Input</dt>
        <dd><var>browsingContext</var>, a <a href="https://html.spec.whatwg.org/multipage/browsers.html#browsing-context">browsing context</a></dd>
      <dt>Output</dt>
        <dd><var>windowClient</var>, a <a href="#window-client-interface">WindowClient</a> object</dd>
    </dl>
    <ol>
      <li>Let <var>windowClient</var> be a new <code><a href="#window-client-interface">WindowClient</a></code> object that represents <var>browsingContext</var>.</li>
      <li>Set <var>windowClient</var>'s <a href="#dfn-service-worker-client-visibilitystate">visibility state</a> to <var>browsingContext</var>'s <a href="https://html.spec.whatwg.org/multipage/browsers.html#active-document">active document</a>'s <a href="http://www.w3.org/TR/page-visibility/#dom-document-visibilitystate">visibilityState</a> attribute value.</li>
      <li>Set <var>windowClient</var>'s <a href="#dfn-service-worker-client-visibilitystate">focus state</a> to the result of running <var>browsingContext</var>'s <a href="https://html.spec.whatwg.org/multipage/browsers.html#active-document">active document</a>'s <a href="https://html.spec.whatwg.org/multipage/interaction.html#dom-document-hasfocus">hasFocus()</a> method.</li>
      <li>Return <var>windowClient</var>.</li>
    </ol>
    </div>
  </section>

  <section title="query-cache-algorithm"><header><span class="section-number">9.19</span> <h3 id="query-cache-algorithm" data-bookmark-label="9.19 Query Cache">Query Cache</h3><span class="anchor"><a style="text-decoration: none;" href="#query-cache-algorithm">¶</a></span></header>


    <div class="algorithm">
    <dl>
      <dt>Input</dt>
        <dd><var>request</var>, a <code><a href="https://fetch.spec.whatwg.org/#request">Request</a></code> object</dd>
        <dd><var>options</var>, a <code><a href="#cache-query-options-dictionary">CacheQueryOptions</a></code> object, optional</dd>
        <dd><var>targetStorage</var>, an array that has [<code><a href="https://fetch.spec.whatwg.org/#request">Request</a></code>, <code><a href="https://fetch.spec.whatwg.org/#response">Response</a></code>] pairs as its elements, optional</dd>
      <dt>Output</dt>
        <dd><var>resultArray</var>, an array that has [<code><a href="https://fetch.spec.whatwg.org/#request">Request</a></code>, <code><a href="https://fetch.spec.whatwg.org/#response">Response</a></code>] pairs as its elements</dd>
    </dl>
    <ol>
      <li>Let <var>requestArray</var> be an empty array.</li>
      <li>Let <var>responseArray</var> be an empty array.</li>
      <li>Let <var>resultArray</var> be an empty array.</li>
      <li>If <var>options</var>.<var>ignoreMethod</var> is false and <var>request</var>.<var>method</var> is neither "<code>GET</code>" nor "<code>HEAD</code>", then:
        <ol>
          <li>Return <var>resultArray</var>.</li>
        </ol>
      </li>
      <li>Let <var>cachedURL</var> and <var>requestURL</var> be null.</li>
      <li>Let <var>serializedCachedURL</var> and <var>serializedRequestURL</var> be null.</li>
      <li>If the optional argument <var>targetStorage</var> is omitted, then:
        <ol>
          <li>For each <a href="#dfn-fetching-record">fetching record</a> <var>entry</var> of its <a href="#dfn-request-to-response-map">request to response map</a>, in key insertion order:
            <ol>
              <li>Set <var>cachedURL</var> to <var>entry</var>.[[key]]'s associated <a href="https://fetch.spec.whatwg.org/#concept-request-request">request</a>'s <a href="https://fetch.spec.whatwg.org/#concept-request-url">url</a>.</li>
              <li>Set <var>requestURL</var> to <var>request</var>'s associated <a href="https://fetch.spec.whatwg.org/#concept-request-request">request</a>'s <a href="https://fetch.spec.whatwg.org/#concept-request-url">url</a>.</li>
              <li>If <var>options</var>.<var>ignoreSearch</var> is true, then:
                <ol>
                  <li>Set <var>cachedURL</var>'s <a href="https://url.spec.whatwg.org/#concept-url-query">query</a> to the empty string.</li>
                  <li>Set <var>requestURL</var>'s <a href="https://url.spec.whatwg.org/#concept-url-query">query</a> to the empty string.</li>
                </ol>
              </li>
              <li>Set <var>serializedCachedURL</var> to <a href="https://url.spec.whatwg.org/#concept-url-serializer">serialized</a> <var>cachedURL</var>.</li>
              <li>Set <var>serializedRequestURL</var> to <a href="https://url.spec.whatwg.org/#concept-url-serializer">serialized</a> <var>requestURL</var>.</li>
              <li>If <var>serializedCachedURL</var> matches <var>serializedRequestURL</var>, then:
                <ol>
                  <li>Add a copy of <var>entry</var>.[[key]] to <var>requestArray</var>.</li>
                  <li>Add a copy of <var>entry</var>.[[value]] to <var>responseArray</var>.</li>
                </ol>
              </li>
            </ol>
          </li>
        </ol>
      </li>
      <li>Else:
        <ol>
          <li>For each <var>record</var> in <var>targetStorage</var>:
            <ol>
              <li>Set <var>cachedURL</var> to <var>record</var>[0]'s associated <a href="https://fetch.spec.whatwg.org/#concept-request-request">request</a>'s <a href="https://fetch.spec.whatwg.org/#concept-request-url">url</a>.</li>
              <li>Set <var>requestURL</var> to <var>request</var>'s associated <a href="https://fetch.spec.whatwg.org/#concept-request-request">request</a>'s <a href="https://fetch.spec.whatwg.org/#concept-request-url">url</a>.</li>
              <li>If <var>options</var>.<var>ignoreSearch</var> is true, then:
                <ol>
                  <li>Set <var>cachedURL</var>'s <a href="https://url.spec.whatwg.org/#concept-url-query">query</a> to the empty string.</li>
                  <li>Set <var>requestURL</var>'s <a href="https://url.spec.whatwg.org/#concept-url-query">query</a> to the empty string.</li>
                </ol>
              </li>
              <li>Set <var>serializedCachedURL</var> to <a href="https://url.spec.whatwg.org/#concept-url-serializer">serialized</a> <var>cachedURL</var>.</li>
              <li>Set <var>serializedRequestURL</var> to <a href="https://url.spec.whatwg.org/#concept-url-serializer">serialized</a> <var>requestURL</var>.</li>
              <li>If <var>serializedCachedURL</var> matches <var>serializedRequestURL</var>, then:
                <ol>
                  <li>Add <var>record</var>[0] to <var>requestArray</var>.</li>
                  <li>Add <var>record</var>[1] to <var>responseArray</var>.</li>
                </ol>
              </li>
            </ol>
          </li>
        </ol>
      </li>
      <li>For each <var>cachedResponse</var> in <var>responseArray</var> with the index <var>index</var>:
        <ol>
          <li>Let <var>cachedRequest</var> be the <var>index</var>th element in <var>requestArray</var>.</li>
          <li>If <var>cachedResponse</var>'s <a href="https://fetch.spec.whatwg.org/#concept-response-response">response</a>'s <a href="https://fetch.spec.whatwg.org/#concept-response-header-list">header list</a> contains no <a href="https://fetch.spec.whatwg.org/#concept-header">header</a> <a href="https://fetch.spec.whatwg.org/#concept-header-name">named</a> `<code>Vary</code>`, or <var>options</var>.<var>ignoreVary</var> is true, then:
            <ol>
              <li>Add an array [<var>cachedRequest</var>, <var>cachedResponse</var>] to <var>resultArray</var>.</li>
              <li>Continue to the next iteration of the loop.</li>
            </ol>
          </li>
          <li>Let <var>varyHeaders</var> be the array containing the elements corresponding to the <a href="https://tools.ietf.org/html/rfc7230#section-3.2">field-values</a> of the <a href="https://tools.ietf.org/html/rfc7231#section-7.1.4">Vary</a> header.</li>
          <li>Let <var>matchFailed</var> be false.</li>
          <li>For each <var>f</var> in <var>varyHeaders</var>:
            <ol>
              <li>If <var>f</var> matches "<code>*</code>", or the result of running <var>cachedRequest</var>.<a href="https://fetch.spec.whatwg.org/#dom-request-headers">headers</a> object's <code><a href="https://fetch.spec.whatwg.org/#dom-headers-get">get(<var>name</var>)</a></code> method with <var>f</var> as the argument does not match the result of running <var>request</var>.<a href="https://fetch.spec.whatwg.org/#dom-request-headers">headers</a> object's <code><a href="https://fetch.spec.whatwg.org/#dom-headers-get">get(<var>name</var>)</a></code> method with <var>f</var> as the argument, then:
                <ol>
                  <li>Set <var>matchFailed</var> to true.</li>
                  <li>Break the loop.</li>
                </ol>
              </li>
            </ol>
          </li>
          <li>If <var>matchFailed</var> is false, then:
            <ol>
              <li>Add an array [<var>cachedRequest</var>, <var>cachedResponse</var>] to <var>resultArray</var>.</li>
            </ol>
          </li>
        </ol>
      </li>
      <li>Return <var>resultArray</var>.</li>
    </ol>
    </div>
  </section>

  <section title="batch-cache-operations-algorithm"><header><span class="section-number">9.20</span> <h3 id="batch-cache-operations-algorithm" data-bookmark-label="9.20 Batch Cache Operations">Batch Cache Operations</h3><span class="anchor"><a style="text-decoration: none;" href="#batch-cache-operations-algorithm">¶</a></span></header>


    <div class="algorithm">
    <dl>
      <dt>Input</dt>
        <dd><var>operations</var>, an array of  <code><a href="#cache-batch-operation-dictionary">CacheBatchOperation</a></code> dictionary objects</dd>
      <dt>Output</dt>
        <dd><var>promise</var>, a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> resolves with an array of <code><a href="https://fetch.spec.whatwg.org/#response">Response</a></code> objects.</dd>
    </dl>
    <ol>
      <li>Let <var>p</var> be a <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-promise-objects">promise</a> resolved with no value.</li>
      <li>Return the result of <a href="http://www.w3.org/2001/tag/doc/promises-guide#transforming-by">transforming</a> <var>p</var> with a fulfillment handler that performs the following substeps in parallel:
        <ol>
          <li>Let <var>itemsCopy</var> be a new <a href="#dfn-request-to-response-map">request to response map</a> that is a copy of its <a href="https://dom.spec.whatwg.org/#context-object">context object</a>'s <a href="#dfn-request-to-response-map">request to response map</a>.</li>
          <li>Let <var>addedRecords</var> be an empty array.</li>
          <li>Try running the following substeps atomically:
            <ol>
              <li>Let <var>resultArray</var> be an empty array.</li>
              <li>For each <var>operation</var> in <var>operations</var> with the index <var>index</var>:
                <ol>
                  <li>If <var>operation</var>.<var>type</var> matches neither "delete" nor "put", then:
                    <ol>
                      <li><a href="http://heycam.github.io/webidl/#dfn-throw">Throw</a> a <code>TypeError</code>.</li>
                    </ol>
                  </li>
                  <li>If <var>operation</var>.<var>type</var> matches "delete" and <var>operation</var>.<var>response</var> is not null, then:
                    <ol>
                      <li><a href="http://heycam.github.io/webidl/#dfn-throw">Throw</a> a <code>TypeError</code>.</li>
                    </ol>
                  </li>
                  <li>If the result of running <a href="#query-cache-algorithm">Query Cache</a> algorithm passing <var>operation</var>.<var>request</var>, <var>operation</var>.<var>options</var>, and <var>addedRecords</var> as the arguments is not an empty array, then:
                    <ol>
                      <li><a href="http://heycam.github.io/webidl/#dfn-throw">Throw</a> an "<code><a href="http://heycam.github.io/webidl/#invalidstateerror">InvalidStateError</a></code>" exception.</li>
                    </ol>
                  </li>
                  <li>Let <var>requestResponseArray</var> be the result of running <a href="#query-cache-algorithm">Query Cache</a> algorithm passing <var>operation</var>.<var>request</var> and <var>operation</var>.<var>options</var> as the arguments.</li>
                  <li>For each <var>requestResponse</var> in <var>requestResponseArray</var>:
                    <ol>
                      <li>If <var>operation</var>.<var>type</var> matches "delete", remove the corresponding <a href="#dfn-fetching-record">fetching record</a> from <a href="#dfn-request-to-response-map">request to response map</a>.</li>
                    </ol>
                  </li>
                  <li>If <var>operation</var>.<var>type</var> matches "put", then:
                    <ol>
                      <li>If <var>operation</var>.<var>response</var> is null, then:
                        <ol>
                          <li><a href="http://heycam.github.io/webidl/#dfn-throw">Throw</a> a <code>TypeError</code>.</li>
                        </ol>
                      </li>
                      <li>Let <var>r</var> be <var>operation</var>.<var>request</var>'s associated <a href="https://fetch.spec.whatwg.org/#concept-request-request">request</a>.</li>
                      <li>If <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-url">url</a>'s <a href="https://url.spec.whatwg.org/#concept-url-scheme">scheme</a> is not one of "<code>http</code>" and "<code>https</code>", then:
                        <ol>
                          <li><a href="http://heycam.github.io/webidl/#dfn-throw">Throw</a> a <code>TypeError</code>.</li>
                        </ol>
                      </li>
                      <li>If <var>r</var>'s <a href="https://fetch.spec.whatwg.org/#concept-request-method">method</a> is not `<code>GET</code>`, then:
                        <ol>
                          <li><a href="http://heycam.github.io/webidl/#dfn-throw">Throw</a> a <code>TypeError</code>.</li>
                        </ol>
                      </li>
                      <li>If <var>operation</var>.<var>options</var> is not null, then:
                        <ol>
                          <li><a href="http://heycam.github.io/webidl/#dfn-throw">Throw</a> a <code>TypeError</code>.</li>
                        </ol>
                      </li>
                      <li>If there exists a corresponding <a href="#dfn-fetching-record">fetching record</a> <var>fetchingRecord</var> for <var>operation</var>.<var>request</var> and <var>operation</var>.<var>response</var> in <a href="#dfn-request-to-response-map">request to response map</a>, set <var>fetchingRecord</var>.[[value]] to <var>operation</var>.<var>response</var>.</li>
                      <li>Else, set a newly-created <a href="#dfn-fetching-record">fetching record</a> {[[key]]: <var>operation</var>.<var>request</var>, [[value]]: <var>operation</var>.<var>response</var>} to <a href="#dfn-request-to-response-map">request to response map</a>.
                        <p class="note">The cache commit is allowed as long as the response's headers are available.</p>
                      </li>
                      <li>If the cache write operation in the previous two steps failed due to exceeding the granted quota limit, <a href="http://heycam.github.io/webidl/#dfn-throw">throw</a> a "<code><a href="http://heycam.github.io/webidl/#quotaexceedederror">QuotaExceededError</a></code>" exception.</li>
                      <li>Add an array [<var>operation</var>.<var>request</var>, <var>operation</var>.<var>response</var>] to <var>addedRecords</var>.</li>
                    </ol>
                  </li>
                  <li>Add <var>operation</var>.<var>response</var> to <var>resultArray</var>.</li>
                </ol>
              </li>
              <li>Return <var>resultArray</var>.</li>
            </ol>
          </li>
          <li>And then, if an exception was <a href="http://heycam.github.io/webidl/#dfn-throw">thrown</a>, then:
            <ol>
              <li>Set the <a href="https://dom.spec.whatwg.org/#context-object">context object</a>'s <a href="#dfn-request-to-response-map">request to response map</a> to <var>itemsCopy</var>.</li>
              <li><a href="http://heycam.github.io/webidl/#dfn-throw">Throw</a> the exception</li>
            </ol>
          </li>
        </ol>
      </li>
    </ol>
    </div>
  </section>

</section>

<section title="acknowledgements"><header><span class="section-number">10</span> <h2 id="acknowledgements" data-bookmark-label="10 Acknowledgements">Acknowledgements</h2><span class="anchor"><a style="text-decoration: none;" href="#acknowledgements">¶</a></span></header>

  <!-- FIXME: INCOMPLETE!! Please add collaborators below. -->

  <p id="acknowledgements.1">Jake Archibald is a ghost-author of this document. The best instincts in the design are his. He similarly shaped many of the details through discussion and experimentation. The bits which are not his (but which are good) owe everything to his experience, persistence, and focus on enabling web developers. He embodies a hopeful example for developers in shaping browser efforts to more directly address real-world pain points. If service workers solve "offline for the web", the credit is due him.</p>

  <p id="acknowledgements.2">Deep thanks go to Andrew Betts for organizing and hosting a small workshop of like-minded individuals including: Jake Archibald, Jackson Gabbard, Tobie Langel, Robin Berjon, Patrick Lauke, Christian Heilmann. From the clarity of the day's discussions and the use-cases outlined there, much has become possible. Further thanks to Andrew for raising consciousness about the offline problem. His organization of EdgeConf and inclusion of Offline as a persistent topic there has created many opportunities and connections that have enabled this work to progress.</p>

  <p id="acknowledgements.3">Anne van Kesteren has generously lent his encyclopedic knowledge of Web Platform arcana and standards development experience throughout the development of the service worker. This specification would be incomplete without his previous work in describing the real-world behavior of URLs, HTTP Fetch, Promises, and DOM. Similarly, this specification would not be possible without Ian Hickson's rigorous Web Worker spec. Much thanks to him.</p>

  <p id="acknowledgements.4">In no particular order, deep gratitude for design guidance and discussion goes to: Jungkee Song, Alec Flett, David Barrett-Kahn, Aaron Boodman, Michael Nordman, Tom Ashworth, Kinuko Yasuda, Darin Fisher, Jonas Sicking, Jesús Leganés Combarro, Mark Christian, Dave Hermann, Yehuda Katz, François Remy, Ilya Grigorik, Will Chan, Domenic Denicola, Nikhil Marathe, Yves Lafon, Adam Barth, Greg Simon, Devdatta Akhawe, Dominic Cooney, Jeffrey Yasskin, Joshua Bell, Boris Zbarsky, Matt Falkenhagen, Tobie Langel, Gavin Peters, Ben Kelly, and Hiroki Nakagawa.</p>

  <p id="acknowledgements.5">Jason Weber, Chris Wilson, Paul Kinlan, Ehsan Akhgari, and Daniel Austin have provided valuable, well-timed feedback on requirements and the standardization process.</p>

  <p id="acknowledgements.6">The authors would also like to thank Dimitri Glazkov for his scripts and formatting tools which have been essential in the production of this specification. The authors are also grateful for his considerable guidance.</p>

  <p id="acknowledgements.7">Thanks also to Vivian Cromwell, Greg Simon, Alex Komoroske, Wonsuk Lee, and Seojin Kim for their considerable professional support.</p>
</section>


</body></html>
